it-swarm.com.de

Stellen Sie richtig fest, ob Datumszeichenfolge ein gültiges Datum in diesem Format ist

Ich erhalte eine Datumszeichenfolge von einer API, die als yyyy-mm-dd formatiert ist.

Ich verwende derzeit einen regulären Ausdruck, um das String-Format zu überprüfen. Dies funktioniert zwar einwandfrei, aber ich kann einige Fälle sehen, in denen es ein korrektes Format entsprechend dem String sein könnte, aber tatsächlich ein ungültiges Datum. beispielsweise 2013-13-01.

Gibt es eine bessere Möglichkeit in PHP, eine Zeichenfolge wie 2013-13-01 zu verwenden, um festzustellen, ob es ein gültiges Datum ist oder nicht für das Format yyyy-mm-dd?

138
Marty Wallace

Sie können DateTime class für diesen Zweck verwenden:

function validateDate($date, $format = 'Y-m-d')
{
    $d = DateTime::createFromFormat($format, $date);
    // The Y ( 4 digits year ) returns TRUE for any integer with any number of digits so changing the comparison from == to === fixes the issue.
    return $d && $d->format($format) === $date;
}

[Funktion aus dieser Antwort . Auch auf php.net . Ursprünglich geschrieben von Glavić .]


Testfälle:

var_dump(validateDate('2013-13-01'));  // false
var_dump(validateDate('20132-13-01')); // false
var_dump(validateDate('2013-11-32'));  // false
var_dump(validateDate('2012-2-25'));   // false
var_dump(validateDate('2013-12-01'));  // true
var_dump(validateDate('1970-12-01'));  // true
var_dump(validateDate('2012-02-29'));  // true
var_dump(validateDate('2012', 'Y'));   // true
var_dump(validateDate('12012', 'Y'));  // false

Demo!

365
Amal Murali

Bestimmen Sie, ob eine Zeichenfolge ein Datum ist

function checkIsAValidDate($myDateString){
    return (bool)strtotime($myDateString);
}
64
arsh

Verwenden Sie auf einfache Weise die PHP-Funktion "Vorgebaut":

function checkmydate($date) {
  $tempDate = explode('-', $date);
  // checkdate(month, day, year)
  return checkdate($tempDate[1], $tempDate[2], $tempDate[0]);
}

Prüfung

   checkmydate('2015-12-01'); //true
   checkmydate('2015-14-04'); //false
29
vineet

Feststellen, ob Zeichenfolge ein Datum ist, auch wenn Zeichenfolge kein Standardformat ist

(strtotime akzeptiert kein benutzerdefiniertes Format)

<?php
function validateDateTime($dateStr, $format)
{
    date_default_timezone_set('UTC');
    $date = DateTime::createFromFormat($format, $dateStr);
    return $date && ($date->format($format) === $dateStr);
}

// These return true
validateDateTime('2001-03-10 17:16:18', 'Y-m-d H:i:s');
validateDateTime('2001-03-10', 'Y-m-d');
validateDateTime('2001', 'Y');
validateDateTime('Mon', 'D');
validateDateTime('March 10, 2001, 5:16 pm', 'F j, Y, g:i a');
validateDateTime('March 10, 2001, 5:16 pm', 'F j, Y, g:i a');
validateDateTime('03.10.01', 'm.d.y');
validateDateTime('10, 3, 2001', 'j, n, Y');
validateDateTime('20010310', 'Ymd');
validateDateTime('05-16-18, 10-03-01', 'h-i-s, j-m-y');
validateDateTime('Monday 8th of August 2005 03:12:46 PM', 'l jS \of F Y h:i:s A');
validateDateTime('Wed, 25 Sep 2013 15:28:57', 'D, d M Y H:i:s');
validateDateTime('17:03:18 is the time', 'H:m:s \i\s \t\h\e \t\i\m\e');
validateDateTime('17:16:18', 'H:i:s');

// These return false
validateDateTime('2001-03-10 17:16:18', 'Y-m-D H:i:s');
validateDateTime('2001', 'm');
validateDateTime('Mon', 'D-m-y');
validateDateTime('Mon', 'D-m-y');
validateDateTime('2001-13-04', 'Y-m-d');
14
migli

Diese Option ist nicht nur einfach, sondern akzeptiert auch fast alle Formate, obwohl sie bei nicht standardmäßigen Formaten fehlerhaft sein kann.

$timestamp = strtotime($date);
return $timestamp ? $date : null;
11
galki

Sie können auch das Datum für das Monat und das Jahr durchsuchen und dann die Funktion PHP checkdate() verwenden, die Sie hier lesen können: http://php.net/manual/de/function.checkdate.php

Sie können dieses auch versuchen:

$date="2013-13-01";

if (preg_match("/^[0-9]{4}-(0[1-9]|1[0-2])-(0[1-9]|[1-2][0-9]|3[0-1])$/",$date))
    {
        echo 'Date is valid';
    }else{
        echo 'Date is invalid';
    }
9
Suvash sarker

Entsprechend der Antwort von cl-sah, aber das klingt besser, kürzer ...

function checkmydate($date) {
  $tempDate = explode('-', $date);
  return checkdate($tempDate[1], $tempDate[2], $tempDate[0]);
}

Prüfung

checkmydate('2015-12-01');//true
checkmydate('2015-14-04');//false
7
Stefano

Ich habe die Sache, dass ich selbst mit PHP gerne funktional -Lösungen finde. Die Antwort von @migli ist zum Beispiel wirklich gut, sehr flexibel und elegant.

Es gibt jedoch ein Problem: Was ist, wenn Sie viele DateTime-Zeichenfolgen mit demselben Format überprüfen müssen? Sie müssten das Format überall wiederholen, was dem Prinzip DRY widerspricht. Wir könnten das Format in eine Konstante setzen, aber wir müssten die Konstante trotzdem an jeden Funktionsaufruf übergeben.

Aber keine Angst mehr! Wir können currying zu unserer Rettung verwenden! PHP macht diese Aufgabe nicht angenehm, aber es ist immer noch möglich, Currying mit PHP zu implementieren:

<?php
function validateDateTime($format)
{
    return function($dateStr) use ($format) {
        $date = DateTime::createFromFormat($format, $dateStr);
        return $date && $date->format($format) === $dateStr;
    };
}

Also, was haben wir gerade gemacht? Grundsätzlich haben wir den Funktionskörper anonymisiert und stattdessen eine solche Funktion zurückgegeben. Wir können die Validierungsfunktion folgendermaßen aufrufen:

validateDateTime('Y-m-d H:i:s')('2017-02-06 17:07:11'); // true

Ja, kein großer Unterschied ... aber die wirkliche Kraft kommt von der partiell angewendeten Funktion, die durch Currying möglich wurde:

// Get a partially applied function
$validate = validateDateTime('Y-m-d H:i:s');

// Now you can use it everywhere, without repeating the format!
$validate('2017-02-06 17:09:31'); // true
$validate('1999-03-31 07:07:07'); // true
$validate('13-2-4 3:2:45'); // false

Funktionale Programmierung FTW!

6

Wie wäre es mit diesem?

Wir verwenden einfach einen Try-Catch-Block. 

$dateTime = 'an invalid datetime';

try {
    $dateTimeObject = new DateTime($dateTime);
} catch (Exception $exc) {
    echo 'Do something with an invalid DateTime';
}

Dieser Ansatz ist nicht nur auf ein Datums-/Zeitformat beschränkt und Sie müssen keine Funktion definieren. 

3
Julian

Der einfachste Weg, um zu überprüfen, ob ein bestimmtes Datum gültig ist, konvertiert es wahrscheinlich in Unixtime, indem es strtotime verwendet, das Format des angegebenen Datums formatiert und dann verglichen wird:

function isValidDate($date) { return date('Y-m-d', strtotime($date)) === $date; }

Natürlich können Sie reguläre Ausdrücke verwenden, um die Gültigkeit zu prüfen. Es ist jedoch auf das angegebene Format beschränkt. Jedes Mal müssen Sie es bearbeiten, um ein anderes Format zu erfüllen, und es wird auch mehr als erforderlich sein. Eingebaute Funktionen sind in den meisten Fällen der beste Weg, um Jobs zu erreichen.

2

Getestete Regex-Lösung:

    function isValidDate($date)
    {
            if (preg_match("/^(((((1[26]|2[048])00)|[12]\d([2468][048]|[13579][26]|0[48]))-((((0[13578]|1[02])-(0[1-9]|[12]\d|3[01]))|((0[469]|11)-(0[1-9]|[12]\d|30)))|(02-(0[1-9]|[12]\d))))|((([12]\d([02468][1235679]|[13579][01345789]))|((1[1345789]|2[1235679])00))-((((0[13578]|1[02])-(0[1-9]|[12]\d|3[01]))|((0[469]|11)-(0[1-9]|[12]\d|30)))|(02-(0[1-9]|1\d|2[0-8])))))$/", $date)) {
                    return $date;
            }
            return null;
    }

Dies gibt Null zurück, wenn das Datum ungültig ist oder nicht im Format JJJJ-MM-TT vorliegt. Andernfalls wird das Datum zurückgegeben.

1
Akumaburn

Validiere mit checkdate function:

$date = '2019-02-30';

$date_parts = explode( '-', $date );

if(checkdate( $date_parts[1], $date_parts[2], $date_parts[0] )){
    //date is valid
}else{
    //date is invalid
}
0
Prince Ahmed

Ich befürchte, dass die Lösung mit den meisten Stimmen ( https://stackoverflow.com/a/19271434/3283279 ) nicht ordnungsgemäß funktioniert. Der vierte Testfall (var_dump (validateDate ('2012-2-25')); // false) ist falsch. Das Datum ist korrekt, weil es dem Format entspricht - der m erlaubt einen Monat, mit oder ohne, der eine Null (siehe: http://php.net/manual/de/datetime). createfromformat.php ). Daher ist ein Datum 2012-2-25 im Format Y-m-d und der Testfall muss true und nicht false sein.

Ich glaube, dass eine bessere Lösung darin besteht, mögliche Fehler wie folgt zu testen:

function validateDate($date, $format = 'Y-m-d') {
    DateTime::createFromFormat($format, $date);
    $errors = DateTime::getLastErrors();

    return $errors['warning_count'] === 0 && $errors['error_count'] === 0;
}
0
Barvajz
/*********************************************************************************
Returns TRUE if the input parameter is a valid date string in "YYYY-MM-DD" format (aka "MySQL date format")
The date separator can be only the '-' character.
*********************************************************************************/
function isMysqlDate($yyyymmdd)
{
    return checkdate(substr($yyyymmdd, 5, 2), substr($yyyymmdd, 8), substr($yyyymmdd, 0, 4)) 
        && (substr($yyyymmdd, 4, 1) === '-') 
        && (substr($yyyymmdd, 7, 1) === '-');
}
0
Marco Demaio