যদিও বর্তমানে গৃহীত উত্তরগুলি আমার পক্ষে একটি বিশাল সহায়ক ছিল, আমি কিছু দরকারী পরিবর্তনগুলি ভাগ করতে চেয়েছিলাম যা অনুসন্ধানগুলি সহজতর করে এবং কর্মক্ষমতা বাড়ায়।
"সাধারণ" পুনরাবৃত্তি ইভেন্ট
নিয়মিত বিরতিতে পুনরাবৃত্তি হওয়া ইভেন্টগুলি পরিচালনা করতে যেমন:
Repeat every other day
অথবা
Repeat every week on Tuesday
আপনার দুটি টেবিল তৈরি করা উচিত, যার events
মধ্যে একটি বলা হয় :
ID NAME
1 Sample Event
2 Another Event
এবং একটি টেবিল এর নামে পরিচিত events_meta
:
ID event_id repeat_start repeat_interval
1 1 1369008000 604800 -- Repeats every Monday after May 20th 2013
1 1 1369008000 604800 -- Also repeats every Friday after May 20th 2013
সঙ্গে repeat_start
কোন সময় (মে 20th 2013 1369008000 অনুরূপ), এবং সঙ্গে একটি UNIX টাইমস্ট্যাম্প তারিখ হচ্ছে repeat_interval
অন্তর মধ্যে একটি পরিমাণ সেকেন্ডের মধ্যে (604800 7 দিন)।
ক্যালেন্ডারে প্রতিটি দিন লুপ করে আপনি এই সাধারণ ক্যোয়ারী ব্যবহার করে পুনরাবৃত্তি ইভেন্টগুলি পেতে পারেন:
SELECT EV.*
FROM `events` EV
RIGHT JOIN `events_meta` EM1 ON EM1.`event_id` = EV.`id`
WHERE (( 1299736800 - repeat_start) % repeat_interval = 0 )
আপনার ক্যালেন্ডারে প্রতিটি তারিখের জন্য কেবল ইউনিক্স-টাইমস্ট্যাম্পে (1299736800) বিকল্প করুন।
মডুলোর ব্যবহার (% চিহ্ন) নোট করুন। এই প্রতীকটি নিয়মিত বিভাগের মতো, তবে ভাগফলের পরিবর্তে '' বাকী '' প্রদান করে এবং বর্তমানের তারিখটি পুনরায়_স্টার্ট থেকে পুনরাবৃত্তিমূলকের একক একাধিক হলে 0 হয়।
পারফরম্যান্স তুলনা
এটি পূর্বে প্রস্তাবিত "মেটা_কিজ" ভিত্তিক উত্তরের চেয়ে উল্লেখযোগ্যভাবে দ্রুত, যা নীচে ছিল:
SELECT EV.*
FROM `events` EV
RIGHT JOIN `events_meta` EM1 ON EM1.`event_id` = EV.`id`
RIGHT JOIN `events_meta` EM2 ON EM2.`meta_key` = CONCAT( 'repeat_interval_', EM1.`id` )
WHERE EM1.meta_key = 'repeat_start'
AND (
( CASE ( 1299132000 - EM1.`meta_value` )
WHEN 0
THEN 1
ELSE ( 1299132000 - EM1.`meta_value` )
END
) / EM2.`meta_value`
) = 1
আপনি যদি এই ক্যোয়ারির ব্যাখ্যা দেন, আপনি নোট করবেন যে এটিতে একটি জয়েন বাফার ব্যবহারের প্রয়োজন ছিল:
+----+-------------+-------+--------+---------------+---------+---------+------------------+------+--------------------------------+
| id | select_type | table | type | possible_keys | key | key_len | ref | rows | Extra |
+----+-------------+-------+--------+---------------+---------+---------+------------------+------+--------------------------------+
| 1 | SIMPLE | EM1 | ALL | NULL | NULL | NULL | NULL | 2 | Using where |
| 1 | SIMPLE | EV | eq_ref | PRIMARY | PRIMARY | 4 | bcs.EM1.event_id | 1 | |
| 1 | SIMPLE | EM2 | ALL | NULL | NULL | NULL | NULL | 2 | Using where; Using join buffer |
+----+-------------+-------+--------+---------------+---------+---------+------------------+------+--------------------------------+
উপরের 1 টি সংযুক্ত সমাধানের জন্য এ জাতীয় কোনও বাফার দরকার নেই।
"জটিল" প্যাটার্নস
এই জাতীয় পুনরাবৃত্ত নিয়মগুলিকে সমর্থন করার জন্য আপনি আরও জটিল ধরণের জন্য সমর্থন যুক্ত করতে পারেন:
Event A repeats every month on the 3rd of the month starting on March 3, 2011
অথবা
Event A repeats second Friday of the month starting on March 11, 2011
আপনার ইভেন্টের টেবিলটি হুবহু দেখতে পাওয়া যাবে:
ID NAME
1 Sample Event
2 Another Event
তারপরে এই জটিল বিধিগুলির জন্য সমর্থন যুক্ত করতে কলামগুলিকে events_meta
পছন্দ করতে যুক্ত করুন :
ID event_id repeat_start repeat_interval repeat_year repeat_month repeat_day repeat_week repeat_weekday
1 1 1369008000 604800 NULL NULL NULL NULL NULL -- Repeats every Monday after May 20, 2013
1 1 1368144000 604800 NULL NULL NULL NULL NULL -- Repeats every Friday after May 10, 2013
2 2 1369008000 NULL 2013 * * 2 5 -- Repeats on Friday of the 2nd week in every month
মনে রাখবেন আপনি কেবল হয় একটি নির্দিষ্ট করতে হবে repeat_interval
বা একটি সেট repeat_year
, repeat_month
, repeat_day
, repeat_week
, এবং repeat_weekday
ডেটা।
এটি একই সাথে উভয় প্রকারের নির্বাচনকে খুব সহজ করে তোলে। প্রতিটি দিন কেবল লুপ করুন এবং সঠিক মানগুলি পূরণ করুন (70 ই জুন 2013 এর জন্য 1370563200 এবং তারপরে বছর, মাস, দিন, সপ্তাহের সংখ্যা এবং সপ্তাহের দিন):
SELECT EV.*
FROM `events` EV
RIGHT JOIN `events_meta` EM1 ON EM1.`event_id` = EV.`id`
WHERE (( 1370563200 - repeat_start) % repeat_interval = 0 )
OR (
(repeat_year = 2013 OR repeat_year = '*' )
AND
(repeat_month = 6 OR repeat_month = '*' )
AND
(repeat_day = 7 OR repeat_day = '*' )
AND
(repeat_week = 2 OR repeat_week = '*' )
AND
(repeat_weekday = 5 OR repeat_weekday = '*' )
AND repeat_start <= 1370563200
)
এটি ২ য় সপ্তাহের শুক্রবারে পুনরাবৃত্তি হওয়া সমস্ত ইভেন্টের পাশাপাশি প্রতি শুক্রবার পুনরাবৃত্তি করে এমন কোনও ইভেন্ট ফেরত দেয়, সুতরাং এটি ইভেন্টের আইডি 1 এবং 2 উভয়ই প্রত্যাবর্তন করে:
ID NAME
1 Sample Event
2 Another Event
* উপরের এসকিউএল-তে সিডিনোট আমি পিএইচপি তারিখের ডিফল্ট সপ্তাহের দিন সূচকগুলি ব্যবহার করেছি, তাই শুক্রবারের জন্য "5"
আশা করি এটি অন্যকে ততটাই সহায়তা করবে যতটা আসল উত্তরটি আমাকে সহায়তা করেছিল!
1299132000
হার্ডকোড কেন আপনি ব্যাখ্যা করতে পারেন ? যদি আমার প্রদত্ত শেষের তারিখের জন্য উপস্থিতি তারিখ এবং ব্যবহারকারী পেতে প্রয়োজন হয় তবে এটি কী করবে?