ব্যক্তিগতভাবে এটি তারিখ হয় বা তারিখ হতে পারে, আমি সর্বদা এটি হিসাবে এক হিসাবে সংরক্ষণ করার পরামর্শ দিই। থাম্বের নিয়ম হিসাবে কাজ করা আরও সহজ।
- একটি তারিখ 4 বাইট।
- একটি ছোট্ট 2 বাইট (আমাদের দুটি প্রয়োজন)
- ... 2 বাইট: বছরের জন্য একটি ছোট
- ... 2 বাইট: এক মাসের জন্য একটি ছোট
আপনার কাছে এমন একটি তারিখ থাকতে পারে যা আপনাকে কখনই প্রয়োজন হলে দিনটিকে সমর্থন করবে অথবা এক smallint
বছর এবং মাসের জন্য এমন একটি দিন যা অতিরিক্ত নির্ভুলতার পক্ষে কখনও সমর্থন করবে না।
নমুনা তথ্য
আসুন এখন একটি উদাহরণ তাকান .. আসুন আমাদের নমুনা জন্য 1 মিলিয়ন তারিখ তৈরি করুন। এটি 1901 এবং 2100 এর মধ্যে 200 বছরের জন্য প্রায় 5000 সারি Every প্রতিবছর প্রতি মাসের জন্য কিছু থাকা উচিত।
CREATE TABLE foo
AS
SELECT
x,
make_date(year,month,1)::date AS date,
year::smallint,
month::smallint
FROM generate_series(1,1e6) AS gs(x)
CROSS JOIN LATERAL CAST(trunc(random()*12+1+x-x) AS int) AS month
CROSS JOIN LATERAL CAST(trunc(random()*200+1901+x-x) AS int) AS year
;
CREATE INDEX ON foo(date);
CREATE INDEX ON foo (year,month);
VACUUM FULL ANALYZE foo;
পরীক্ষামূলক
সহজ WHERE
এখন আমরা তারিখটি ব্যবহার না করার এই তত্ত্বগুলি পরীক্ষা করতে পারি .. আমি এই কয়েকটি বার কয়েকবার চালিয়েছি যাতে জিনিস গরম করতে পারে।
EXPLAIN ANALYZE SELECT * FROM foo WHERE date = '2014-1-1'
QUERY PLAN
--------------------------------------------------------------------------------------------------------------------------
Bitmap Heap Scan on foo (cost=11.56..1265.16 rows=405 width=14) (actual time=0.164..0.751 rows=454 loops=1)
Recheck Cond: (date = '2014-04-01'::date)
Heap Blocks: exact=439
-> Bitmap Index Scan on foo_date_idx (cost=0.00..11.46 rows=405 width=0) (actual time=0.090..0.090 rows=454 loops=1)
Index Cond: (date = '2014-04-01'::date)
Planning time: 0.090 ms
Execution time: 0.795 ms
এখন, আসুন তাদের সাথে পৃথক করে অন্য পদ্ধতিটি চেষ্টা করি
EXPLAIN ANALYZE SELECT * FROM foo WHERE year = 2014 AND month = 1;
QUERY PLAN
--------------------------------------------------------------------------------------------------------------------------------
Bitmap Heap Scan on foo (cost=12.75..1312.06 rows=422 width=14) (actual time=0.139..0.707 rows=379 loops=1)
Recheck Cond: ((year = 2014) AND (month = 1))
Heap Blocks: exact=362
-> Bitmap Index Scan on foo_year_month_idx (cost=0.00..12.64 rows=422 width=0) (actual time=0.079..0.079 rows=379 loops=1)
Index Cond: ((year = 2014) AND (month = 1))
Planning time: 0.086 ms
Execution time: 0.749 ms
(7 rows)
নিখরচায়, তারা সব 0.749 নয় .. কিছু কিছু বেশি বা কম, তবে এতে কিছু আসে যায় না। তারা সব তুলনামূলকভাবে এক। এটি সহজভাবে প্রয়োজন হয় না।
এক মাসের মধ্যে
এখন, আসুন আমরা এটির সাথে মজা করি .. আসুন যাক আপনি যোন 2014 এর 1 মাসের মধ্যে (একই মাসে আমরা উপরে ব্যবহার করেছি) সমস্ত অন্তর খুঁজে পেতে চাই।
EXPLAIN ANALYZE
SELECT *
FROM foo
WHERE date
BETWEEN
('2014-1-1'::date - '1 month'::interval)::date
AND ('2014-1-1'::date + '1 month'::interval)::date;
QUERY PLAN
---------------------------------------------------------------------------------------------------------------------------
Bitmap Heap Scan on foo (cost=21.27..2310.97 rows=863 width=14) (actual time=0.384..1.644 rows=1226 loops=1)
Recheck Cond: ((date >= '2013-12-01'::date) AND (date <= '2014-02-01'::date))
Heap Blocks: exact=1083
-> Bitmap Index Scan on foo_date_idx (cost=0.00..21.06 rows=863 width=0) (actual time=0.208..0.208 rows=1226 loops=1)
Index Cond: ((date >= '2013-12-01'::date) AND (date <= '2014-02-01'::date))
Planning time: 0.104 ms
Execution time: 1.727 ms
(7 rows)
সম্মিলিত পদ্ধতির সাথে এটি তুলনা করুন
EXPLAIN ANALYZE
SELECT *
FROM foo
WHERE year = 2013 AND month = 12
OR ( year = 2014 AND ( month = 1 OR month = 2) );
QUERY PLAN
--------------------------------------------------------------------------------------------------------------------------------------------
Bitmap Heap Scan on foo (cost=38.79..2999.66 rows=1203 width=14) (actual time=0.664..2.291 rows=1226 loops=1)
Recheck Cond: (((year = 2013) AND (month = 12)) OR (((year = 2014) AND (month = 1)) OR ((year = 2014) AND (month = 2))))
Heap Blocks: exact=1083
-> BitmapOr (cost=38.79..38.79 rows=1237 width=0) (actual time=0.479..0.479 rows=0 loops=1)
-> Bitmap Index Scan on foo_year_month_idx (cost=0.00..12.64 rows=421 width=0) (actual time=0.112..0.112 rows=402 loops=1)
Index Cond: ((year = 2013) AND (month = 12))
-> BitmapOr (cost=25.60..25.60 rows=816 width=0) (actual time=0.218..0.218 rows=0 loops=1)
-> Bitmap Index Scan on foo_year_month_idx (cost=0.00..12.62 rows=420 width=0) (actual time=0.108..0.108 rows=423 loops=1)
Index Cond: ((year = 2014) AND (month = 1))
-> Bitmap Index Scan on foo_year_month_idx (cost=0.00..12.38 rows=395 width=0) (actual time=0.108..0.108 rows=401 loops=1)
Index Cond: ((year = 2014) AND (month = 2))
Planning time: 0.256 ms
Execution time: 2.421 ms
(13 rows)
এটি উভয় ধীর এবং কুরুচিপূর্ণ।
GROUP BY
/ORDER BY
সংযুক্ত পদ্ধতি,
EXPLAIN ANALYZE
SELECT date, count(*)
FROM foo
GROUP BY date
ORDER BY date;
QUERY PLAN
--------------------------------------------------------------------------------------------------------------------------
Sort (cost=20564.75..20570.75 rows=2400 width=4) (actual time=286.749..286.841 rows=2400 loops=1)
Sort Key: date
Sort Method: quicksort Memory: 209kB
-> HashAggregate (cost=20406.00..20430.00 rows=2400 width=4) (actual time=285.978..286.301 rows=2400 loops=1)
Group Key: date
-> Seq Scan on foo (cost=0.00..15406.00 rows=1000000 width=4) (actual time=0.012..70.582 rows=1000000 loops=1)
Planning time: 0.094 ms
Execution time: 286.971 ms
(8 rows)
এবং আবার যৌগিক পদ্ধতিতে
EXPLAIN ANALYZE
SELECT year, month, count(*)
FROM foo
GROUP BY year, month
ORDER BY year, month;
QUERY PLAN
--------------------------------------------------------------------------------------------------------------------------
Sort (cost=23064.75..23070.75 rows=2400 width=4) (actual time=336.826..336.908 rows=2400 loops=1)
Sort Key: year, month
Sort Method: quicksort Memory: 209kB
-> HashAggregate (cost=22906.00..22930.00 rows=2400 width=4) (actual time=335.757..336.060 rows=2400 loops=1)
Group Key: year, month
-> Seq Scan on foo (cost=0.00..15406.00 rows=1000000 width=4) (actual time=0.010..70.468 rows=1000000 loops=1)
Planning time: 0.098 ms
Execution time: 337.027 ms
(8 rows)
উপসংহার
সাধারণত, স্মার্ট লোকদের কঠোর পরিশ্রম করতে দিন। ডেটম্যাথ শক্ত, আমার ক্লায়েন্টরা আমাকে যথেষ্ট পরিমাণে বেতন দেয় না। আমি এই পরীক্ষা করতাম। আমি হার্ড কি কখনো এই উপসংহারে আমি চেয়ে ভাল ফলাফল পেতে পারে যে চাপা ছিল date
। আমি চেষ্টা বন্ধ করে দিয়েছি।
আপডেট
@a_horse_with_no_name এক মাস পরীক্ষার মধ্যে আমার জন্য প্রস্তাবিত WHERE (year, month) between (2013, 12) and (2014,2)
। আমার মতে, শীতল হওয়ার সময় এটি আরও জটিল কোয়েরি এবং লাভ না হলে আমি এড়াতে চাই। হায়, এটি নিকটতম হলেও এটি এখনও ধীর ছিল - যা এই পরীক্ষা থেকে বেশি দূরে নেওয়া away এটি কেবল খুব বেশি কিছু দেয় না।
EXPLAIN ANALYZE
SELECT *
FROM foo
WHERE (year, month) between (2013, 12) and (2014,2);
QUERY PLAN
--------------------------------------------------------------------------------------------------------------------------------------
Bitmap Heap Scan on foo (cost=5287.16..15670.20 rows=248852 width=14) (actual time=0.753..2.157 rows=1226 loops=1)
Recheck Cond: ((ROW(year, month) >= ROW(2013, 12)) AND (ROW(year, month) <= ROW(2014, 2)))
Heap Blocks: exact=1083
-> Bitmap Index Scan on foo_year_month_idx (cost=0.00..5224.95 rows=248852 width=0) (actual time=0.550..0.550 rows=1226 loops=1)
Index Cond: ((ROW(year, month) >= ROW(2013, 12)) AND (ROW(year, month) <= ROW(2014, 2)))
Planning time: 0.099 ms
Execution time: 2.249 ms
(7 rows)
month
যাতে দুটি পূর্ণসংখ্যা থাকে। তবে আমি মনে করি আপনি যদি কখনও কখনও মাসের দিনের প্রয়োজন না হয় তবে দুটি পূর্ণসংখ্যার ব্যবহার করা সম্ভবত সহজতর