2008-09-01 10 views
34

Jaki jest wzór RegEx dla DateTime (2008-09-01 12:35:45)?Jaki jest wzór wyrażenia regularnego dla datetime (2008-09-01 12:35:45)?

otrzymuję ten błąd:

No ending delimiter '^' found

Zastosowanie:

preg_match('(?n:^(?=\d)((?<day>31(?!(.0?[2469]|11))|30(?!.0?2)|29(?(.0?2)(?=.{3,4}(1[6-9]|[2-9]\d)(0[48]|[2468][048]|[13579][26])|(16|[2468][048]|[3579][26])00))|0?[1-9]|1\d|2[0-8])(?<sep>[/.-])(?<month>0?[1-9]|1[012])\2(?<year>(1[6-9]|[2-9]\d)\d{2})(?:(?=\x20\d)\x20|$))?(?<time>((0?[1-9]|1[012])(:[0-5]\d){0,2}(?i:\ [AP]M))|([01]\d|2[0-3])(:[0-5]\d){1,2})?$)', '2008-09-01 12:35:45'); 

daje ten błąd:

Warning: preg_match() [function.preg-match]: Compilation failed: nothing to repeat at offset 0 in E:\www\index.php on line 19

Odpowiedz

42

@Espo: Muszę powiedzieć, że regex jest niesamowite. Nie chciałbym pisać kodu, który zrobiłby coś przydatnego w dopasowaniach, na przykład, gdybyś chciał dowiedzieć się, jaka data i godzina wpisał użytkownik.

Wydaje się, że rozwiązaniem Toma byłoby bardziej obronić, gdyż jest o czasy zillion prostsze i z dodatkiem niektórych nawiasach można łatwo dostać się do wartości użytkownik wpisał:

(\d{4})-(\d{2})-(\d{2}) (\d{2}):(\d{2}):(\d{2}) 

Jeśli” Ponownie użyj wartości perl, a następnie możesz uzyskać wartości w taki sposób:

$year = $1; 
$month = $2; 
$day = $3; 
$hour = $4; 
$minute = $5; 
$second = $6; 

Inne języki będą miały podobne możliwości. Zauważ, że będziesz musiał wprowadzić drobne mody do wyrażenia regularnego, jeśli chcesz akceptować wartości takie jak jednocyfrowe miesiące.

+3

Tylko komentarz, aby powiedzieć, że to wyrażenie nie wykryje, jeśli data, miesiąc lub godzina ma wartość lepszą do maksimum. Na przykład zadziała 2012-65-65 99:99:99. Poza tym regex jest świetny! – darkheir

+0

Zgadzam się, że to nie jest dobre do sprawdzania poprawności daty. –

+1

Wyrażone wyrażenie regularne nie ma na celu potwierdzenia daty. Ma na celu sprawdzenie * składni * ciągu znaków, aby sprawdzić, czy może to być data. Po uzyskaniu wartości można sprawdzić poprawność podanej daty za pomocą normalnych funkcji biblioteki daty. –

6

http://regexlib.com/REDetails.aspx?regexp_id=610

^(?=\d)(?:(?:31(?!.(?:0?[2469]|11))|(?:30|29)(?!.0?2)|29(?=.0?2.(?:(?:(?:1[6-9]|[2-9]\d)?(?:0[48]|[2468][048]|[13579][26])|(?:(?:16|[2468][048]|[3579][26])00)))(?:\x20|$))|(?:2[0-8]|1\d|0?[1-9]))([-./])(?:1[012]|0?[1-9])\1(?:1[6-9]|[2-9]\d)?\d\d(?:(?=\x20\d)\x20|$))?(((0?[1-9]|1[012])(:[0-5]\d){0,2}(\x20[AP]M))|([01]\d|2[0-3])(:[0-5]\d){1,2})?$


This RE validates both dates and/or times patterns. Days in Feb. are also validated for Leap years. Dates: in dd/mm/yyyy or d/m/yy format between 1/1/1600 - 31/12/9999. Leading zeroes are optional. Date separators can be either matching dashes(-), slashes(/) or periods(.) Times: in the hh:MM:ss AM/PM 12 hour format (12:00 AM - 11:59:59 PM) or hh:MM:ss military time format (00:00:00 - 23:59:59). The 12 hour time format: 1) may have a leading zero for the hour. 2) Minutes and seconds are optional for the 12 hour format 3) AM or PM is required and case sensitive. Military time 1) must have a leading zero for all hours less than 10. 2) Minutes are manditory. 3) seconds are optional. Datetimes: combination of the above formats. A date first then a time separated by a space. ex) dd/mm/yyyy hh:MM:ss


Edit: Upewnij się, że kopia regex ze strony regexlib.com jak StackOverflow czasami usuwa/niszczy znaki specjalne.

+0

Ta odpowiedź jest dobrym wyrażenie regularne, ale nie jest to odpowiedź na pytanie actuall. Pytanie dotyczy sprawdzania dat oddzielonych "-", a nie "/", jak opisuje to odpowiedź. –

21

prosta wersja, która będzie pracować dla formatu wspomniano, ale nie wszyscy inni, jak na @Espos:

(\d{4}-\d{2}-\d{2} \d{2}:\d{2}:\d{2}) 
+0

plus jedno najprostsze rozwiązanie! – chiliNUT

+0

Ten zatwierdza zarówno 0000-00-00 00:00:00, jak i 0000-00-00 00:00 (\ d {4}) - (\ d {2}) - (\ d {2}) (\ d {2}): (\ d {2})? ((:)? (\ D {2})) – iRector

-1

Funkcje PHP preg muszą być opatrzone wyrażeniem ograniczającym, którym może być dowolna postać. Nie możesz używać tego znaku ogranicznika bez ucieczki w regex. To powinno działać (tu znak separatora jest /):

preg_match('/\d{4}-\d{2}-\d{2} \d{2}:\d{2}:\d{2}/', '2008-09-01 12:35:45'); 

// or this, to allow matching 0:00:00 time too. 
preg_match('/\d{4}-\d{2}-\d{2} \d{1,2}:\d{2}:\d{2}/', '2008-09-01 12:35:45'); 

Jeśli trzeba dopasować linie, które zawierają tylko datetime, dodaj^i $ na początku i na końcu wyrażenia regularnego.

preg_match('/^\d{4}-\d{2}-\d{2} \d{2}:\d{2}:\d{2}$/', '2008-09-01 12:35:45'); 

Link to PHP Manual's preg_match()

0

regarding Imran odpowiedź Od września 2008 na 12:33 1TH jest tam brakuje: w strukturze poprawne wzory są

preg_match('/\d{4}-\d{2}-\d{2} \d{2}:\d{2}:\d{2}/', '2008-09-01 12:35:45', $m1); 
print_r($m1); 
preg_match('/\d{4}-\d{2}-\d{2} \d{1,2}:\d{2}:\d{2}/', '2008-09-01 12:35:45', $m2); 
print_r($m2); 
preg_match('/^\d{4}-\d{2}-\d{2} \d{2}:\d{2}:\d{2}$/', '2008-09-01 12:35:45', $m3); 
print_r($m3); 

to zwraca

Array ([0] => 2008-09-01 12:35:45) 
Array ([0] => 2008-09-01 12:35:45) 
Array ([0] => 2008-09-01 12:35:45) 
1
^([2][0]\d{2}\/([0]\d|[1][0-2])\/([0-2]\d|[3][0-1]))$|^([2][0]\d{2}\/([0]\d|[1][0-2])\/([0-2]\d|[3][0-1])\s([0-1]\d|[2][0-3])\:[0-5]\d\:[0-5]\d)$ 
3
$date = "2014-04-01 12:00:00"; 

preg_match('/(\d{4})-(\d{2})-(\d{2}) (\d{2}):(\d{2}):(\d{2})/',$date, $matches); 

print_r($matches); 

$ mecze będą:

Array ( 
    [0] => 2014-04-01 12:00:00 
    [1] => 2014 
    [2] => 04 
    [3] => 01 
    [4] => 12 
    [5] => 00 
    [6] => 00 
) 

Łatwym sposobem rozbić datetime sformatowany ciąg.

-1

Oto uproszczona wersja (pochodzi z odpowiedzi Espo). Sprawdza poprawność daty (nawet rok przestępny) i hh: mm: ss jest opcjonalne
Przykłady, które działają:
- 31/12/2003 11:59:59
- 29-2-2004

^(?=\d)(?:(?:31(?!.(?:0?[2469]|11))|(?:30|29)(?!.0?2)|29(?=.0?2.(?:(?:(?:1[6-9]|[2-9]\d)?(?:0[48]|[2468][048]|[13579][26])|(?:(?:16|[2468][048]|[3579][26])00)))(?:\x20|$))|(?:2[0-8]|1\d|0?[1-9]))([-./])(?:1[012]|0?[1-9])\1(?:1[6-9]|[2-9]\d)?\d\d(?:(?=\x20\d)\x20|$))(|([01]\d|2[0-3])(:[0-5]\d){1,2})?$ 
0

Oto moje rozwiązanie:

/^(2[0-9]{3})-(0[1-9]|1[012])-(0[1-9]|[12][0-9]|3[01]) (0[0-9]|1[0-9]|2[0123])\:([][0-9])\:([][0-9])$/u 
0

I zmodyfikowany wzór wyrażenia regularnego http://regexlib.com/REDetails.aspx?regexp_id=610. Poniższy wzór powinien pasować do Twojego przypadku.

^(?=\d)(?:(?:1[6-9]|[2-9]\d)?\d\d([-.\/])(?:1[012]|0?[1-9])\1(?:31(?<!.(?:0[2469]|11))|(?:30|29)(?<!.02)|29(?=.0?2.(?:(?:(?:1[6-9]|[2-9]\d)?(?:0[48]|[2468][048]|[13579][26])|(?:(?:16|[2468][048]|[3579][26])00)))(?:\x20|$))|(?:2[0-8]|1\d|0?[1-9]))(?:(?=\x20\d)\x20|$))?(((0?[1-9]|1[012])(:[0-5]\d){0,2}(\x20[AP]M))|([01]\d|2[0-3])(:[0-5]\d){1,2})?$ 

YYYY-MM-DD HH: MM: SS

Powiązane problemy