Converti un formato data in un altro in PHP


336

Esiste un modo semplice per convertire un formato data in un altro formato data in PHP?

Ho questo:

$old_date = date('y-m-d-h-i-s');            // works

$middle = strtotime($old_date);             // returns bool(false)

$new_date = date('Y-m-d H:i:s', $middle);   // returns 1970-01-01 00:00:00

Ma ovviamente mi piacerebbe che tornasse una data attuale piuttosto che il crack all'alba. Che cosa sto facendo di sbagliato?



Risposte:


293

Il secondo parametro date()deve essere un indicatore orario corretto (secondi dal 1 ° gennaio 1970). Stai passando una stringa, che date () non può riconoscere.

Puoi usare strtotime () per convertire una stringa di data in un timestamp. Tuttavia, anche strtotime () non riconosce il y-m-d-h-i-sformato.

PHP 5.3 e versioni successive

Usa DateTime::createFromFormat. Ti permette di specificare una maschera esatta - usando la date()sintassi - con cui analizzare le date delle stringhe in arrivo.

PHP 5.2 e versioni precedenti

Dovrai analizzare gli elementi (anno, mese, giorno, ora, minuti, secondi) manualmente substr()e consegnare i risultati a mktime () che ti costruirà un timestamp.

Ma è un sacco di lavoro! Consiglio di usare un formato diverso che strftime () possa capire. strftime () comprende qualsiasi data immessa a corto di the next time joe will slip on the ice. ad esempio, funziona:

$old_date = date('l, F d y h:i:s');              // returns Saturday, January 30 10 02:06:34
$old_date_timestamp = strtotime($old_date);
$new_date = date('Y-m-d H:i:s', $old_date_timestamp);   

Grazie Pekka, appena modificato la mia domanda, ci ha provato ma non sembra funzionare.
Tom,

Ho modificato la risposta mentre l'hai accettata :) Ho aggiunto altri esempi e riferimenti.
Pekka,

Gotcha, questo è davvero il problema. È un nome file fisso che devo riconvertire in una data (deve essere in quel formato), quindi scoprirò una soluzione alternativa.
Tom,

Nota: Secondo php.net DateTimeesiste dal momento che PHP 5.2 in PHP core e supporto sperimentale DateTimepossono essere abilitati per PHP 5.1 al momento della compilazione. secure.php.net/manual/en/datetime.installation.php
Charlotte Dunois,

108

Il modo più semplice per farlo è

$myDateTime = DateTime::createFromFormat('Y-m-d', $dateString);
$newDateString = $myDateTime->format('m/d/Y');

Prima gli stai dando il formato $ dateString. Quindi gli stai dicendo il formato in cui vuoi $ newDateString.

Questo evita anche l'uso di strtotime, che a volte può essere difficile da lavorare.

Se non stai trasformando da un formato di data a un altro, ma desideri solo la data corrente (o datetime) in un formato specifico, è ancora più semplice:

$now = new DateTime();
$timestring = $now->format('Y-m-d h:i:s');

Quest'altra domanda si riferisce anche allo stesso argomento: Converti formato data aaaa-mm-gg => gg-mm-aaaa .


E come è duplicato se ho posto la domanda prima di quella a cui ti riferisci?
Tom,

1
Ho modificato la risposta. Volevo solo sottolineare che queste due domande dovrebbero essere collegate in qualche modo.
Ceiroa,

disponibile su php 5.3+
Zorox,

$timestring = $now->format('Y-m-d h:i:s');certamente? mper mesi, iper minuti
Mark Baker,


53

Le basi

Il modo più semplice per convertire un formato data in un altro è usare strtotime()con date(). strtotime()convertirà la data in un timestamp Unix . Quel timestamp Unix può quindi essere passato a date()per convertirlo nel nuovo formato.

$timestamp = strtotime('2008-07-01T22:35:17.02');
$new_date_format = date('Y-m-d H:i:s', $timestamp);

O come one-liner:

$new_date_format = date('Y-m-d H:i:s', strtotime('2008-07-01T22:35:17.02'));

Tieni presente che strtotime()richiede che la data sia in un formato valido . La mancata fornitura di un formato valido comporterà la strtotime()restituzione di false che causeranno la data del 1969-12-31.

utilizzando DateTime()

A partire da PHP 5.2, PHP ha offerto la DateTime()classe che ci offre strumenti più potenti per lavorare con le date (e l'ora). Possiamo riscrivere il codice sopra usando DateTime()così:

$date = new DateTime('2008-07-01T22:35:17.02');
$new_date_format = $date->format('Y-m-d H:i:s');

Lavorare con i timestamp Unix

date() accetta un timeatamp Unix come secondo parametro e restituisce una data formattata per te:

$new_date_format = date('Y-m-d H:i:s', '1234567890');

DateTime () funziona con i timestamp Unix aggiungendo un @prima del timestamp:

$date = new DateTime('@1234567890');
$new_date_format = $date->format('Y-m-d H:i:s');

Se il timestamp che hai è in millisecondi (potrebbe terminare 000e / o il timestamp è lungo tredici caratteri) dovrai convertirlo in secondi prima di poterlo convertire in un altro formato. Esistono due modi per farlo:

  • Tagliare le ultime tre cifre usando substr()

Il taglio delle ultime tre cifre può essere raggiunto in diversi modi, ma l'utilizzo substr()è il più semplice:

$timestamp = substr('1234567899000', -3);
  • Dividi il substrato per 1000

È inoltre possibile convertire il timestamp in secondi dividendo per 1000. Poiché il timestamp è troppo grande per i sistemi a 32 bit per eseguire la matematica, sarà necessario utilizzare la libreria BCMath per eseguire la matematica come stringhe:

$timestamp = bcdiv('1234567899000', '1000');

Per ottenere un timestamp Unix è possibile utilizzare strtotime()quale restituisce un timestamp Unix:

$timestamp = strtotime('1973-04-18');

Con DateTime () è possibile utilizzare DateTime::getTimestamp()

$date = new DateTime('2008-07-01T22:35:17.02');
$timestamp = $date->getTimestamp();

Se usi PHP 5.2 puoi invece usare l' Uopzione di formattazione:

$date = new DateTime('2008-07-01T22:35:17.02');
$timestamp = $date->format('U');

Lavorare con formati di data non standard e ambigui

Sfortunatamente non tutte le date con cui uno sviluppatore deve lavorare sono in un formato standard. Fortunatamente PHP 5.3 ci ha fornito una soluzione per questo. DateTime::createFromFormat()ci permette di dire a PHP in quale formato è una stringa di data in modo che possa essere analizzata con successo in un oggetto DateTime per ulteriori manipolazioni.

$date = DateTime::createFromFormat('F-d-Y h:i A', 'April-18-1973 9:48 AM');
$new_date_format = $date->format('Y-m-d H:i:s');

In PHP 5.4 abbiamo acquisito la possibilità di aggiungere l'accesso ai membri della classe all'istanza che ci consente di trasformare il nostro DateTime()codice in una riga:

$new_date_format = (new DateTime('2008-07-01T22:35:17.02'))->format('Y-m-d H:i:s');

$new_date_format = DateTime::createFromFormat('F-d-Y h:i A', 'April-18-1973 9:48 AM')->format('Y-m-d H:i:s');

27

Prova questo:

$old_date = date('y-m-d-h-i-s');
$new_date = date('Y-m-d H:i:s', strtotime($old_date));

Non funzionerà, strtotime () non riconosce il formato. Ho appena provato.
Pekka,

d'accordo, ho appena inserito il codice del formato dall'interrogatore, dovrebbe essere specificato il formato corretto.
Sarfraz,

Ha funzionato per me. Il mio $ old_date era qualcosa del genere 22/05/2012 T19: 16: 37 + 01: 00. Grazie comunque!
VishwaKumar,

15

Per convertire $dateda dd-mm-yyyy hh:mm:ssun datetime MySQL corretto vado in questo modo:

$date = DateTime::createFromFormat('d-m-Y H:i:s',$date)->format('Y-m-d H:i:s');

4
Non dovresti concatenare questi metodi a meno che tu non sia sicuro al 110% che $ date sia una data valida e si adatti al formato. Con questo detto, una data non valida che non corrisponde esattamente al formato tornerà: Fatal error: Call to a member function format() on a non-object. Solo un avviso!
Half Crazed,

È vero, una soluzione migliore è farlo in 3 passaggi con un controllo null come passaggio intermedio.
Jelle de Fries,

11

Di seguito è riportato un metodo semplice per convertire le date in diversi formati.

// Create a new DateTime object
$date = DateTime::createFromFormat('Y-m-d', '2016-03-25');

// Output the date in different formats
echo $date->format('Y-m-d')."\n";
echo $date->format('d-m-Y')."\n";
echo $date->format('m-d-Y')."\n";

10
$old_date = date('y-m-d-h-i-s');       // works

stai sbagliando qui, questo dovrebbe essere

$old_date = date('y-m-d h:i:s');       // works

il separatore del tempo è ':'


Penso che questo aiuterà ...

$old_date = date('y-m-d-h-i-s');              // works

preg_match_all('/(\d+)-(\d+)-(\d+)-(\d+)-(\d+)-(\d+)/', $old_date, $out, PREG_SET_ORDER);
$out = $out[0];
$time = mktime($out[4], $out[5], $out[6], $out[2], $out[3], $out[1]);

$new_date = date('Y-m-d H:i:s', $time); 

O


$old_date = date('y-m-d-h-i-s');              // works

$out = explode('-', $old_date);
$time = mktime($out[3], $out[4], $out[5], $out[1], $out[2], $out[0]);

$new_date = date('Y-m-d H:i:s', $time); 

Sì, certo grazie, è un nome file GUID che desidero riconvertire in un formato data adeguato.
Tom,

8

Questo modo nativo aiuterà a convertire qualsiasi formato immesso nel formato desiderato.

$formatInput = 'd-m-Y'; //Give any format here, this would be converted into your format
$dateInput = '01-02-2018'; //date in above format

$formatOut = 'Y-m-d'; // Your format
$dateOut = DateTime::createFromFormat($formatInput, $dateInput)->format($formatOut);


7

strtotime lo risolverà. le date non sono tutte uguali e tutte nel nostro formato.

<?php
$e1 = strtotime("2013-07-22T12:00:03Z");
echo date('y.m.d H:i', $e1);
echo "2013-07-22T12:00:03Z";

$e2 = strtotime("2013-07-23T18:18:15Z");
echo date ('y.m.d H:i', $e2);
echo "2013-07-23T18:18:15Z";

$e1 = strtotime("2013-07-21T23:57:04Z");
echo date ('y.m.d H:i', $e2);
echo "2013-07-21T23:57:04Z";
?>

5

Prova questo:

$tempDate = explode('-','03-23-15');
$date = '20'.$tempDate[2].'-'.$tempDate[0].'-'.$tempDate[1];

5

Questo risolto per me,

$old = '18-04-2018';
$new = date('Y-m-d', strtotime($old));
echo $new;

Uscita: 18-04-2018


2

Questo è l'altro modo per convertire il formato della data

 <?php
$pastDate = "Tuesday 11th October, 2016";
$pastDate = str_replace(",","",$pastDate);

$date = new DateTime($pastDate);
$new_date_format = $date->format('Y-m-d');

echo $new_date_format.' 23:59:59'; ?>

1

Solo usando le stringhe, per me è una buona soluzione, meno problemi con mysql. Rileva il formato corrente e lo modifica se necessario, questa soluzione è solo per il formato spagnolo / francese e inglese, senza utilizzare la funzione phetime datetime.

class dateTranslator {

 public static function translate($date, $lang) {
      $divider = '';

      if (empty($date)){
           return null;   
      }
      if (strpos($date, '-') !== false) {
           $divider = '-';
      } else if (strpos($date, '/') !== false) {
           $divider = '/';
      }
      //spanish format DD/MM/YYYY hh:mm
      if (strcmp($lang, 'es') == 0) {

           $type = explode($divider, $date)[0];
           if (strlen($type) == 4) {
                $date = self::reverseDate($date,$divider);
           } 
           if (strcmp($divider, '-') == 0) {
                $date = str_replace("-", "/", $date);
           }
      //english format YYYY-MM-DD hh:mm
      } else {

           $type = explode($divider, $date)[0];
           if (strlen($type) == 2) {

                $date = self::reverseDate($date,$divider);
           } 
           if (strcmp($divider, '/') == 0) {
                $date = str_replace("/", "-", $date);

           }   
      }
      return $date;
 }

 public static function reverseDate($date) {
      $date2 = explode(' ', $date);
      if (count($date2) == 2) {
           $date = implode("-", array_reverse(preg_split("/\D/", $date2[0]))) . ' ' . $date2[1];
      } else {
           $date = implode("-", array_reverse(preg_split("/\D/", $date)));
      }

      return $date;
 }

USO

dateTranslator::translate($date, 'en')

1

So che questo è vecchio, ma, incappando in un fornitore che utilizza in modo incoerente 5 diversi formati di data nelle loro API (e test server con una varietà di versioni di PHP dai 5 agli ultimi 7), ho deciso di scrivere un convertitore universale che funziona con una miriade di versioni di PHP.

Questo convertitore prenderà praticamente qualsiasi input, incluso qualsiasi formato standard di data / ora (incluso con o senza millisecondi) e qualsiasi rappresentazione del Tempo Epoch (incluso con o senza millisecondi) e lo convertirà praticamente in qualsiasi altro formato.

Per chiamarlo:

$TheDateTimeIWant=convertAnyDateTome_toMyDateTime([thedateIhave],[theformatIwant]);

L'invio di null per il formato renderà la funzione restituisce il datetime in Epoch / Unix Time. Altrimenti, invia qualsiasi stringa di formato supportata da date (), nonché con ".u" per i millisecondi (gestisco anche i millisecondi, anche se date () restituisce zeri).

Ecco il codice:

        <?php   
        function convertAnyDateTime_toMyDateTime($dttm,$dtFormat)
        {
            if (!isset($dttm))
            {
                return "";
            }
            $timepieces = array();
            if (is_numeric($dttm))
            {
                $rettime=$dttm;
            }
            else
            {
                $rettime=strtotime($dttm);
                if (strpos($dttm,".")>0 and strpos($dttm,"-",strpos($dttm,"."))>0)
                {
                    $rettime=$rettime.substr($dttm,strpos($dttm,"."),strpos($dttm,"-",strpos($dttm,"."))-strpos($dttm,"."));
                    $timepieces[1]="";
                }
                else if (strpos($dttm,".")>0 and strpos($dttm,"-",strpos($dttm,"."))==0)
                {               
                    preg_match('/([0-9]+)([^0-9]+)/',substr($dttm,strpos($dttm,"."))." ",$timepieces);
                    $rettime=$rettime.".".$timepieces[1];
                }
            }

            if (isset($dtFormat))
            {
                // RETURN as ANY date format sent
                if (strpos($dtFormat,".u")>0)       // Deal with milliseconds
                {
                    $rettime=date($dtFormat,$rettime);              
                    $rettime=substr($rettime,0,strripos($rettime,".")+1).$timepieces[1];                
                }
                else                                // NO milliseconds wanted
                {
                    $rettime=date($dtFormat,$rettime);
                }
            }
            else
            {
                // RETURN Epoch Time (do nothing, we already built Epoch Time)          
            }
            return $rettime;    
        }
    ?>

Ecco alcune chiamate di esempio: noterai che gestisce anche tutti i dati del fuso orario (anche se, come notato sopra, qualsiasi orario non GMT viene restituito nel tuo fuso orario).

        $utctime1="2018-10-30T06:10:11.2185007-07:00";
        $utctime2="2018-10-30T06:10:11.2185007";
        $utctime3="2018-10-30T06:10:11.2185007 PDT";
        $utctime4="2018-10-30T13:10:11.2185007Z";
        $utctime5="2018-10-30T13:10:11Z";
        $dttm="10/30/2018 09:10:11 AM EST";

        echo "<pre>";
        echo "<b>Epoch Time to a standard format</b><br>";
        echo "<br>Epoch Tm: 1540905011    to STD DateTime     ----RESULT: ".convertAnyDateTime_toMyDateTime("1540905011","Y-m-d H:i:s")."<hr>";
        echo "<br>Epoch Tm: 1540905011          to UTC        ----RESULT: ".convertAnyDateTime_toMyDateTime("1540905011","c");
        echo "<br>Epoch Tm: 1540905011.2185007  to UTC        ----RESULT: ".convertAnyDateTime_toMyDateTime("1540905011.2185007","c")."<hr>";
        echo "<b>Returned as Epoch Time (the number of seconds that have elapsed since 00:00:00 Thursday, 1 January 1970, Coordinated Universal Time (UTC), minus leap seconds.)";
        echo "</b><br>";
        echo "<br>UTCTime1: ".$utctime1." ----RESULT: ".convertAnyDateTime_toMyDateTime($utctime1,null);
        echo "<br>UTCTime2: ".$utctime2."       ----RESULT: ".convertAnyDateTime_toMyDateTime($utctime2,null);
        echo "<br>UTCTime3: ".$utctime3."   ----RESULT: ".convertAnyDateTime_toMyDateTime($utctime3,null);
        echo "<br>UTCTime4: ".$utctime4."      ----RESULT: ".convertAnyDateTime_toMyDateTime($utctime4,null);
        echo "<br>UTCTime5: ".$utctime5."              ----RESULT: ".convertAnyDateTime_toMyDateTime($utctime5,null);
        echo "<br>NO MILIS: ".$dttm."        ----RESULT: ".convertAnyDateTime_toMyDateTime($dttm,null);
        echo "<hr>";
        echo "<hr>";
        echo "<b>Returned as whatever datetime format one desires</b>";
        echo "<br>UTCTime1: ".$utctime1." ----RESULT: ".convertAnyDateTime_toMyDateTime($utctime1,"Y-m-d H:i:s")."              Y-m-d H:i:s";
        echo "<br>UTCTime2: ".$utctime2."       ----RESULT: ".convertAnyDateTime_toMyDateTime($utctime2,"Y-m-d H:i:s.u")."      Y-m-d H:i:s.u";
        echo "<br>UTCTime3: ".$utctime3."   ----RESULT: ".convertAnyDateTime_toMyDateTime($utctime3,"Y-m-d H:i:s.u")."      Y-m-d H:i:s.u";
        echo "<p><b>Returned as ISO8601</b>";
        echo "<br>UTCTime3: ".$utctime3."   ----RESULT: ".convertAnyDateTime_toMyDateTime($utctime3,"c")."        ISO8601";
        echo "</pre>";

Ecco l'output:

Epoch Tm: 1540905011                        ----RESULT: 2018-10-30 09:10:11

Epoch Tm: 1540905011          to UTC        ----RESULT: 2018-10-30T09:10:11-04:00
Epoch Tm: 1540905011.2185007  to UTC        ----RESULT: 2018-10-30T09:10:11-04:00
Returned as Epoch Time (the number of seconds that have elapsed since 00:00:00 Thursday, 1 January 1970, Coordinated Universal Time (UTC), minus leap seconds.)

UTCTime1: 2018-10-30T06:10:11.2185007-07:00 ----RESULT: 1540905011.2185007
UTCTime2: 2018-10-30T06:10:11.2185007       ----RESULT: 1540894211.2185007
UTCTime3: 2018-10-30T06:10:11.2185007 PDT   ----RESULT: 1540905011.2185007
UTCTime4: 2018-10-30T13:10:11.2185007Z      ----RESULT: 1540905011.2185007
UTCTime5: 2018-10-30T13:10:11Z              ----RESULT: 1540905011
NO MILIS: 10/30/2018 09:10:11 AM EST        ----RESULT: 1540908611
Returned as whatever datetime format one desires
UTCTime1: 2018-10-30T06:10:11.2185007-07:00 ----RESULT: 2018-10-30 09:10:11              Y-m-d H:i:s
UTCTime2: 2018-10-30T06:10:11.2185007       ----RESULT: 2018-10-30 06:10:11.2185007      Y-m-d H:i:s.u
UTCTime3: 2018-10-30T06:10:11.2185007 PDT   ----RESULT: 2018-10-30 09:10:11.2185007      Y-m-d H:i:s.u
Returned as ISO8601
UTCTime3: 2018-10-30T06:10:11.2185007 PDT   ----RESULT: 2018-10-30T09:10:11-04:00        ISO8601

L'unica cosa non presente in questa versione è la possibilità di selezionare il fuso orario in cui si desidera inserire il datetime restituito. Inizialmente, l'ho scritto per modificare qualsiasi datetime in Epoch Time, quindi non avevo bisogno del supporto del fuso orario. È banale aggiungere però.

Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.