Kalendarz Powtarzające Się / Powtarzające Się Wydarzenia-Najlepsza Metoda Przechowywania
Buduję niestandardowy system zdarzeń, a jeśli masz powtarzające się zdarzenie, które wygląda tak:
Event a powtarza się co 4 dni od 3 marca 2011
LUB
Event B powtarza się co 2 tygodnie we wtorek począwszy od 1 marca 2011
Jak mogę to zapisać w bazie danych w sposób, który ułatwi wyszukiwanie. Nie chcę problemów z wydajnością, jeśli jest duża liczba zdarzeń, i muszę przejść przez każdy z nich podczas renderowania kalendarz.
11 answers
Przechowywanie" Prostych " Powtarzających Się Wzorców
W moim kalendarzu opartym na PHP/MySQL chciałem przechowywać powtarzające się/powtarzające się informacje o zdarzeniach tak efektywnie, jak to tylko możliwe. Nie chciałem mieć dużej liczby wierszy i chciałem łatwo wyszukać wszystkie wydarzenia, które miały miejsce w określonej dacie.
Poniższa metoda jest świetna w przechowywaniu powtarzających się informacji, które występują w regularnych odstępach czasu, takich jak codziennie, co n dni, co tydzień, co miesiąc co rok, itp itd. Dotyczy to również wzorców typowania we wtorek i czwartek, ponieważ są one przechowywane oddzielnie, jak co tydzień, począwszy od wtorku i co tydzień, począwszy od czwartku.
Zakładając, że mam dwie tabele, jedna o nazwie events
tak:
ID NAME
1 Sample Event
2 Another Event
I tabelę o nazwie events_meta
w ten sposób:
ID event_id meta_key meta_value
1 1 repeat_start 1299132000
2 1 repeat_interval_1 432000
Repeat_start jest datą bez czasu jako znacznik czasu Uniksa, a repeat_interval jest wartością w sekundach między interwałami (432000 to 5 dni).
Repeat_interval_1 przechodzi z repeat_start ID 1. Więc jeśli mam zdarzenie, które powtarza się w każdy wtorek i w każdy czwartek, repeat_interval będzie wynosił 604800( 7 dni) i będą 2 repeat_starts i 2 repeat_intervals. Tabela wyglądałaby tak:
ID event_id meta_key meta_value
1 1 repeat_start 1298959200 -- This is for the Tuesday repeat
2 1 repeat_interval_1 604800
3 1 repeat_start 1299132000 -- This is for the Thursday repeat
4 1 repeat_interval_3 604800
5 2 repeat_start 1299132000
6 2 repeat_interval_5 1 -- Using 1 as a value gives us an event that only happens once
Następnie, jeśli masz kalendarz, który zapętla się każdego dnia, chwytając wydarzenia Dla dnia, w którym jest, zapytanie wyglądałoby tak:
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
LIMIT 0 , 30
Zastąpienie {current_timestamp}
znacznikiem czasu Uniksa dla bieżącej daty (Minus czas, więc wartości godzin, minut i sekund zostaną ustawione na 0).
Mam nadzieję, że to pomoże również komuś innemu!
Przechowywanie" Złożonych " Powtarzających Się Wzorców
Ta metoda lepiej nadaje się do przechowywania złożonych wzorców, takich jak
Event A repeats every month on the 3rd of the month starting on March 3, 2011
Lub
Event A repeats Friday of the 2nd week of the month starting on March 11, 2011
Polecam połączenie tego z powyższym systemem, aby uzyskać największą elastyczność. Tabele do tego powinny wyglądać następująco:
ID NAME
1 Sample Event
2 Another Event
I tabelę o nazwie events_meta
Jak to:
ID event_id meta_key meta_value
1 1 repeat_start 1299132000 -- March 3rd, 2011
2 1 repeat_year_1 *
3 1 repeat_month_1 *
4 1 repeat_week_im_1 2
5 1 repeat_weekday_1 6
repeat_week_im
reprezentuje tydzień bieżącego miesiąca, który potencjalnie może wynosić od 1 do 5. repeat_weekday
w dniu tygodnia, 1-7.
Teraz zakładając, że przeglądasz dni / tygodnie, aby utworzyć widok miesiąca w kalendarzu, możesz skomponować zapytanie takie jak:
SELECT EV . *
FROM `events` AS EV
JOIN `events_meta` EM1 ON EM1.event_id = EV.id
AND EM1.meta_key = 'repeat_start'
LEFT JOIN `events_meta` EM2 ON EM2.meta_key = CONCAT( 'repeat_year_', EM1.id )
LEFT JOIN `events_meta` EM3 ON EM3.meta_key = CONCAT( 'repeat_month_', EM1.id )
LEFT JOIN `events_meta` EM4 ON EM4.meta_key = CONCAT( 'repeat_week_im_', EM1.id )
LEFT JOIN `events_meta` EM5 ON EM5.meta_key = CONCAT( 'repeat_weekday_', EM1.id )
WHERE (
EM2.meta_value =2011
OR EM2.meta_value = '*'
)
AND (
EM3.meta_value =4
OR EM3.meta_value = '*'
)
AND (
EM4.meta_value =2
OR EM4.meta_value = '*'
)
AND (
EM5.meta_value =6
OR EM5.meta_value = '*'
)
AND EM1.meta_value >= {current_timestamp}
LIMIT 0 , 30
To w połączeniu z powyższą metodą można połączyć, aby pokryć większość powtarzających się/powtarzających się wzorców zdarzeń. Jeśli coś przeoczyłem proszę zostawić komentarz.
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2015-02-01 12:01:10
Chociaż obecnie akceptowana odpowiedź była dla mnie ogromną pomocą, chciałem podzielić się kilkoma przydatnymi modyfikacjami, które upraszczają zapytania, a także zwiększają wydajność.
"Proste" Powtarzanie Zdarzeń
Do obsługi zdarzeń powtarzających się w regularnych odstępach czasu, takich jak:
Repeat every other day
Lub
Repeat every week on Tuesday
Powinieneś utworzyć dwie tabele, jedna o nazwie events
w następujący sposób:
ID NAME
1 Sample Event
2 Another Event
I tabelę o nazwie events_meta
w ten sposób:
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
With repeat_start
being a Unix timestamp Data bez czasu (1369008000 odpowiada 20 maja 2013) i repeat_interval
kwota w sekundach między interwałami (604800 to 7 dni).
Poprzez zapętlenie każdego dnia w kalendarzu możesz uzyskać powtarzające się zdarzenia za pomocą tego prostego zapytania:
SELECT EV.*
FROM `events` EV
RIGHT JOIN `events_meta` EM1 ON EM1.`event_id` = EV.`id`
WHERE (( 1299736800 - repeat_start) % repeat_interval = 0 )
Wystarczy zastąpić uniksowy znacznik czasu (1299736800) dla każdej daty w kalendarzu.
Zwróć uwagę na użycie znaku modulo ( % ). Symbol ten jest jak regularny podział, ale Zwraca "resztę" zamiast ilorazu i jako taki wynosi 0, gdy bieżąca data jest dokładną wielokrotnością repeat_interval z repeat_start.
Porównanie Wydajności
Jest to znacznie szybsza odpowiedź niż sugerowana wcześniej odpowiedź "meta_keys", która była następująca:]}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
Jeśli uruchomisz EXPLAIN to zapytanie, zauważysz, że wymagało ono użycia bufora przyłączeniowego:
+----+-------------+-------+--------+---------------+---------+---------+------------------+------+--------------------------------+
| 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 |
+----+-------------+-------+--------+---------------+---------+---------+------------------+------+--------------------------------+
Rozwiązanie z 1 łącznikiem powyżej nie wymaga takiego bufora.
"Złożone" Wzory
Możesz dodawanie obsługi bardziej złożonych typów, aby obsługiwać te typy reguł powtarzania:
Event A repeats every month on the 3rd of the month starting on March 3, 2011
Lub
Event A repeats second Friday of the month starting on March 11, 2011
Twoja tabela zdarzeń może wyglądać dokładnie tak samo:
ID NAME
1 Sample Event
2 Another Event
Następnie, aby dodać obsługę tych złożonych reguł dodaj kolumny do events_meta
w następujący sposób:
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
Zauważ, że po prostu musisz podać repeat_interval
lub zestaw repeat_year
, repeat_month
, repeat_day
, repeat_week
, i repeat_weekday
dane.
To sprawia, że wybór obu typów jednocześnie jest bardzo prosty. Wystarczy przełączyć 1370563200 dla 7 czerwca 2013, a następnie Rok, Miesiąc, Dzień, numer tygodnia i Dzień tygodnia w następujący sposób):
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
)
Zwraca wszystkie zdarzenia, które powtarzają się w piątek drugiego tygodnia, , jak również wszelkie zdarzenia, które powtarzają się w każdy piątek, więc zwraca zarówno Zdarzenie o ID 1, jak i 2:
ID NAME
1 Sample Event
2 Another Event
W tym przypadku nie jest to możliwe, ale jest to możliwe tylko w przypadku, gdy nie jest to możliwe.]}
Mam nadzieję, że to pomoże innym tak bardzo jak oryginalna odpowiedź mi pomogła!
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2015-02-01 12:00:53
Dla wszystkich, którzy są zainteresowani tym, teraz Można po prostu skopiować i wkleić, aby rozpocząć w ciągu kilku minut. Skorzystałem z porad w komentarzach najlepiej jak mogłem. Daj znać, jeśli coś przeoczę.
"WERSJA ZŁOŻONA": {]}
Wydarzenia
+----------+----------------+ | ID | NAME | +----------+----------------+ | 1 | Sample event 1 | | 2 | Second event | | 3 | Third event | +----------+----------------+
Events_meta
+----+----------+--------------+------------------+-------------+--------------+------------+-------------+----------------+ | ID | event_id | repeat_start | repeat_interval | repeat_year | repeat_month | repeat_day | repeat_week | repeat_weekday | +----+----------+--------------+------------------+-------------+--------------+------------+-------------+----------------+ | 1 | 1 | 2014-07-04 | 7 | NULL | NULL | NULL | NULL | NULL | | 2 | 2 | 2014-06-26 | NULL | 2014 | * | * | 2 | 5 | | 3 | 3 | 2014-07-04 | NULL | * | * | * | * | 5 | +----+----------+--------------+------------------+-------------+--------------+------------+-------------+----------------+
Kod SQL:
CREATE TABLE IF NOT EXISTS `events` (
`ID` int(11) NOT NULL AUTO_INCREMENT,
`NAME` varchar(255) NOT NULL,
PRIMARY KEY (`ID`)
) ENGINE=MyISAM DEFAULT CHARSET=utf8 AUTO_INCREMENT=7 ;
--
-- Dumping data for table `events`
--
INSERT INTO `events` (`ID`, `NAME`) VALUES
(1, 'Sample event'),
(2, 'Another event'),
(3, 'Third event...');
CREATE TABLE IF NOT EXISTS `events_meta` (
`ID` int(11) NOT NULL AUTO_INCREMENT,
`event_id` int(11) NOT NULL,
`repeat_start` date NOT NULL,
`repeat_interval` varchar(255) NOT NULL,
`repeat_year` varchar(255) NOT NULL,
`repeat_month` varchar(255) NOT NULL,
`repeat_day` varchar(255) NOT NULL,
`repeat_week` varchar(255) NOT NULL,
`repeat_weekday` varchar(255) NOT NULL,
PRIMARY KEY (`ID`),
UNIQUE KEY `ID` (`ID`)
) ENGINE=MyISAM DEFAULT CHARSET=utf8 AUTO_INCREMENT=6 ;
--
-- Dumping data for table `events_meta`
--
INSERT INTO `events_meta` (`ID`, `event_id`, `repeat_start`, `repeat_interval`, `repeat_year`, `repeat_month`, `repeat_day`, `repeat_week`, `repeat_weekday`) VALUES
(1, 1, '2014-07-04', '7', 'NULL', 'NULL', 'NULL', 'NULL', 'NULL'),
(2, 2, '2014-06-26', 'NULL', '2014', '*', '*', '2', '5'),
(3, 3, '2014-07-04', 'NULL', '*', '*', '*', '*', '1');
Dostępny również jako MySQL export (dla łatwego dostępu)
Indeks przykładowego kodu PHP.php:
<?php
require 'connect.php';
$now = strtotime("yesterday");
$pushToFirst = -11;
for($i = $pushToFirst; $i < $pushToFirst+30; $i++)
{
$now = strtotime("+".$i." day");
$year = date("Y", $now);
$month = date("m", $now);
$day = date("d", $now);
$nowString = $year . "-" . $month . "-" . $day;
$week = (int) ((date('d', $now) - 1) / 7) + 1;
$weekday = date("N", $now);
echo $nowString . "<br />";
echo $week . " " . $weekday . "<br />";
$sql = "SELECT EV.*
FROM `events` EV
RIGHT JOIN `events_meta` EM1 ON EM1.`event_id` = EV.`id`
WHERE ( DATEDIFF( '$nowString', repeat_start ) % repeat_interval = 0 )
OR (
(repeat_year = $year OR repeat_year = '*' )
AND
(repeat_month = $month OR repeat_month = '*' )
AND
(repeat_day = $day OR repeat_day = '*' )
AND
(repeat_week = $week OR repeat_week = '*' )
AND
(repeat_weekday = $weekday OR repeat_weekday = '*' )
AND repeat_start <= DATE('$nowString')
)";
foreach ($dbConnect->query($sql) as $row) {
print $row['ID'] . "\t";
print $row['NAME'] . "<br />";
}
echo "<br /><br /><br />";
}
?>
Przykładowy kod PHP połącz się.php:
<?
// ----------------------------------------------------------------------------------------------------
// Connecting to database
// ----------------------------------------------------------------------------------------------------
// Database variables
$username = "";
$password = "";
$hostname = "";
$database = "";
// Try to connect to database and set charset to UTF8
try {
$dbConnect = new PDO("mysql:host=$hostname;dbname=$database;charset=utf8", $username, $password);
$dbConnect->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);
} catch(PDOException $e) {
echo 'ERROR: ' . $e->getMessage();
}
// ----------------------------------------------------------------------------------------------------
// / Connecting to database
// ----------------------------------------------------------------------------------------------------
?>
Również kod php jest dostępny tutaj (dla lepszej czytelności):
indeks.php
oraz
połącz się.php
Przygotowanie tego zajmie ci kilka minut. Nie godziny. :)
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2014-07-12 19:35:57
Enhancement: zamień znacznik czasu na datę
Jako małe rozszerzenie przyjętej odpowiedzi, która została następnie udoskonalona przez ahoffnera - możliwe jest użycie formatu daty zamiast znacznika czasu. Zalety:
- czytelne daty w bazie danych
- brak problemu z latami > 2038 i znacznikiem czasu
- usuwa trzeba uważać na znaczniki czasu, które są oparte na terminach dostosowanych sezonowo tj. w Wielkiej Brytanii 28 czerwca zaczyna się godzinę wcześniej niż 28 grudnia tak więc wyprowadzenie znacznika czasu z daty może złamać algorytm rekurencji.
Aby to zrobić, zmień DB repeat_start
, który ma być przechowywany jako typ "date" I repeat_interval
przechowuj teraz dni, a nie sekundy. tj. 7 przez 7 dni.
Zmień linię sql: WHERE ((1370563200-repeat_start) % repeat_interval = 0)
To: WHERE (DATEDIFF ('2013-6-7', event_start) % repeat_interval = 0)
Wszystko inne pozostaje takie samo. Simples!Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2014-06-30 10:51:57
Podczas gdy proponowane rozwiązania działają, próbowałem zaimplementować z pełnym kalendarzem i wymagałoby to ponad 90 wywołań baz danych dla każdego widoku( ponieważ ładuje bieżący, poprzedni i następny miesiąc), co, nie byłem zbyt zachwycony.
Znalazłem bibliotekę rekurencji https://github.com/tplaner/When gdzie po prostu przechowujesz reguły w bazie danych i jedno zapytanie, aby pobrać wszystkie odpowiednie reguły.
Mam nadzieję, że to pomoże komuś innemu, ponieważ spędziłem tak wiele godzin próbując znaleźć dobre rozwiązanie.
Edit: ta Biblioteka jest dla PHP
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2016-10-17 13:47:35
Dlaczego nie użyć mechanizmu podobnego do zadań Apache cron? http://en.wikipedia.org/wiki/Cron
Dla kalendarza \ scheduling użyłbym nieco innych wartości dla "bitów", aby pomieścić standardowe zdarzenia powtarzania kalendarza - zamiast [dzień tygodnia (0 - 7), miesiąc (1 - 12), dzień miesiąca (1 - 31), godzina (0 - 23), min (0-59)]
-- użyłbym czegoś takiego [Rok (powtórz co N lat), miesiąc (1 - 12), dzień miesiąca (1 - 31), tydzień miesiąca (1-5), dzień tygodnia (0 - 7)]
Mam nadzieję, że to pomoże.
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2011-08-08 22:21:03
Podążałbym za tym przewodnikiem: https://github.com/bmoeskau/Extensible/blob/master/recurrence-overview.md
Upewnij się również, że używasz formatu iCal, aby nie odkrywać koła na nowo i pamiętaj Zasada #0: nie przechowuj pojedynczych powtarzających się wystąpień zdarzeń jako wierszy w bazie danych!
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2017-01-05 15:51:41
Brzmi bardzo podobnie do zdarzeń MySQL, które są przechowywane w tabelach systemowych. Możesz spojrzeć na strukturę i dowiedzieć się, które kolumny nie są potrzebne:
EVENT_CATALOG: NULL
EVENT_SCHEMA: myschema
EVENT_NAME: e_store_ts
DEFINER: jon@ghidora
EVENT_BODY: SQL
EVENT_DEFINITION: INSERT INTO myschema.mytable VALUES (UNIX_TIMESTAMP())
EVENT_TYPE: RECURRING
EXECUTE_AT: NULL
INTERVAL_VALUE: 5
INTERVAL_FIELD: SECOND
SQL_MODE: NULL
STARTS: 0000-00-00 00:00:00
ENDS: 0000-00-00 00:00:00
STATUS: ENABLED
ON_COMPLETION: NOT PRESERVE
CREATED: 2006-02-09 22:36:06
LAST_ALTERED: 2006-02-09 22:36:06
LAST_EXECUTED: NULL
EVENT_COMMENT:
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2013-03-22 13:33:18
Stworzyłem ezoteryczny język programowania właśnie do tego przypadku. Najlepsze jest to, że jest mniej schematów i niezależny od platformy. Wystarczy, że napiszesz program selektora do swojego harmonogramu, którego składnia jest ograniczona zestawem reguł opisanych tutaj -
Https://github.com/tusharmath/sheql/wiki/Rules
Zasady są rozszerzalne i można dodać dowolny rodzaj dostosowywania w oparciu o rodzaj logiki powtórzeń, które chcesz wykonać, bez martwiąc się o migracje schematów itp.
Jest to zupełnie inne podejście i może mieć swoje wady.
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2014-11-14 15:40:13
@ Rogue Coder
To jest świetne!Możesz po prostu użyć operacji modulo (MOD lub % w mysql), aby Kod był prosty na końcu:
Zamiast:
AND (
( CASE ( 1299132000 - EM1.`meta_value` )
WHEN 0
THEN 1
ELSE ( 1299132000 - EM1.`meta_value` )
END
) / EM2.`meta_value`
) = 1
Do:
$current_timestamp = 1299132000 ;
AND ( ('$current_timestamp' - EM1.`meta_value` ) MOD EM2.`meta_value`) = 1")
Aby pójść dalej, można uwzględnić wydarzenia, które nie powtarzają się na zawsze.
Można dodać coś w rodzaju "repeat_interval_1_end" oznaczającego datę ostatniej "repeat_interval_1". To jednak sprawia, że zapytanie jest bardziej skomplikowane i nie mogę naprawdę dowiedzieć się, jak to zrobić to ...
Może ktoś mógłby pomóc!Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2012-10-03 07:53:50
Dwa przykłady, które podałeś są bardzo proste; można je przedstawić jako prosty przedział (pierwszy to cztery dni, drugi to 14 dni). Sposób modelowania będzie zależał całkowicie od złożoności Twoich nawrotów. Jeśli to, co masz powyżej, jest naprawdę takie proste, Zapisz datę początkową i liczbę dni w przedziale powtórzeń.
Jeśli jednak musisz wspierać takie rzeczy jak
Event A powtarza się co miesiąc 3 dnia miesiąca rozpoczynającego się 3 marca, 2011
LUB
Event a powtarza drugi piątek miesiąca od 11 marca 2011
To jest o wiele bardziej złożony wzór.
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2011-03-03 16:41:12