Estou tentando obter uma data formatada, incluindo microssegundos de milissegundos.
O único problema é que continuo recebendo 000000
date("m-d-Y H:i:s.u", $milliseconds/1000);
ex. 28/07/2013 11: 26: 14,000000
Estou tentando obter uma data formatada, incluindo microssegundos de milissegundos.
O único problema é que continuo recebendo 000000
date("m-d-Y H:i:s.u", $milliseconds/1000);
ex. 28/07/2013 11: 26: 14,000000
Respostas:
php.net diz:
Microssegundos (adicionado no PHP 5.2.2). Observe que
date()
sempre será gerado,000000
já que leva um parâmetro inteiro, ao passo queDateTime::format()
oferece suporte a microssegundos se tiverDateTime
sido criado com microssegundos.
Portanto, use o mais simples:
$micro_date = microtime();
$date_array = explode(" ",$micro_date);
$date = date("Y-m-d H:i:s",$date_array[1]);
echo "Date: $date:" . $date_array[0]."<br>";
Recomendado e usar a dateTime()
classe do referenciado:
$t = microtime(true);
$micro = sprintf("%06d",($t - floor($t)) * 1000000);
$d = new DateTime( date('Y-m-d H:i:s.'.$micro, $t) );
print $d->format("Y-m-d H:i:s.u"); // note at point on "u"
A nota u
é microssegundos (1 segundo = 1000000 µs).
Outro exemplo de php.net :
$d2=new DateTime("2012-07-08 11:14:15.889342");
Referência de dateTime()
em php.net
Eu respondi a pergunta tão curta e simplificada para o autor. Consulte para obter mais informações ao autor: obtendo o formato de data mdY H: i: su de milissegundos
microtime(false)
nenhum deles.)
Você pode fazer isso prontamente com o formato de entrada U.u
.
$now = DateTime::createFromFormat('U.u', microtime(true));
echo $now->format("m-d-Y H:i:s.u");
Isso produz a seguinte saída:
04-13-2015 05:56:22.082300
Na página de manual do PHP para formatos de data:
http://php.net/manual/en/function.date.php
Obrigado a giggsey por apontar uma falha em minha resposta original, acrescentando number_format()
à linha deve corrigir a caixa do segundo exato. Que pena que não parece mais tão elegante ...
$now = DateTime::createFromFormat('U.u', number_format(microtime(true), 6, '.', ''));
http://php.net/manual/en/function.number-format.php
Uma nota sobre os fusos horários em resposta ao DaVe.
Normalmente, o createFromFormat()
método usará o fuso horário local se nenhum for especificado.
http://php.net/manual/en/datetime.createfromformat.php
No entanto, a técnica descrita aqui é inicializar o objeto DateTime usando microtime()
que retorna o número de segundos decorridos desde a época do Unix (01 de janeiro de 1970 00:00:00 GMT).
http://php.net/manual/en/function.microtime.php
Isso significa que o objeto DateTime é inicializado implicitamente em UTC, o que é adequado para tarefas internas do servidor que desejam apenas rastrear o tempo decorrido.
Se precisar exibir a hora para um fuso horário específico, você precisará defini-lo de acordo. No entanto, isso deve ser feito como uma etapa separada após a inicialização ( não usando o terceiro parâmetro de createFromFormat()
) por causa das razões discutidas acima.
O setTimeZone()
método pode ser usado para cumprir esse requisito.
http://php.net/manual/en/datetime.settimezone.php
Como um exemplo:
$now = DateTime::createFromFormat('U.u', number_format(microtime(true), 6, '.', ''));
echo $now->format("m-d-Y H:i:s.u") . '<br>';
$local = $now->setTimeZone(new DateTimeZone('Australia/Canberra'));
echo $local->format("m-d-Y H:i:s.u") . '<br>';
Produz a seguinte saída:
10-29-2015 00:40:09.433818
10-29-2015 11:40:09.433818
Observe que se você deseja inserir no mysql, o formato da hora precisa ser:
format("Y-m-d H:i:s.u")
DateTime::createFromFormat('U.u', microtime(true));
retornará falso se for microtime(true)
executado no segundo exato. Ele retorna '1438616239' em vez de '1438616239.000000'.
number_format
é sempre necessário, mesmo quando não está no segundo exato. Caso contrário, você estará à mercê da precision
opção de configuração do PHP (para "exibição"), que não é alta o suficiente por padrão no PHP 7.0, causando uma perda de precisão (não precisa até o microssegundo).
Aqui está uma abordagem um pouco mais curta. Em vez de trabalhar para criar uma data / hora numérica de alta precisão, converto o valor de microssegundo em uma string, removo o 0
e o adiciono ao final da string de data / hora. Posso cortar facilmente o número de decimais ajustando o parâmetro de comprimento da corda; aqui eu uso 4
para obter milissegundos, mas você poderia usar 7
para obter microssegundos.
$t = explode(" ",microtime());
echo date("m-d-y H:i:s",$t[1]).substr((string)$t[0],1,4);
Para um valor microtime () de 0.98236000 1407400573
, retorna 08-07-14 01:08:13.982
.
echo date('m-d-Y H:i:s').substr(fmod(microtime(true), 1), 1);
exemplo de saída:
02-06-2019 16:45:03.53811192512512
Se você precisar limitar o número de casas decimais, a linha abaixo (mgutt de crédito) seria uma boa alternativa. (Com o código abaixo, o 6 limita o número de casas decimais a 6.)
echo date('m-d-Y H:i:').sprintf('%09.6f', date('s')+fmod(microtime(true), 1));
exemplo de saída:
02-11-2019 15:33:03.624493
echo date('m-d-Y H:i:').sprintf('%09.6f', date('s')+fmod(microtime(true), 1));
. Explicação do motivo pelo qual precisamos 09
: stackoverflow.com/a/28739819/318765
echo date('H:i:s').substr(fmod(microtime(true), 1), 1, 7);
substr()
não arredondar. E, em combinação com round()
ele, cortaria os zeros finais: stackoverflow.com/questions/7493305/… Esse é o motivo pelo qual propus sprintf()
.
Se você deseja formatar uma data como a do JavaScript (new Date()).toISOString()
por algum motivo, é assim que você pode fazer em PHP:
$now = microtime(true);
gmdate('Y-m-d\TH:i:s', $now).sprintf('.%03dZ',round(($now-floor($now))*1000));
Saída de amostra:
2016-04-27T18:25:56.696Z
Apenas para provar que subtrair o número inteiro não reduz a precisão da parte decimal:
>>> number_format(123.01234567890123456789,25)
=> "123.0123456789012408307826263"
>>> number_format(123.01234567890123456789-123,25)
=> "0.0123456789012408307826263"
PHP fez em volta das casas decimais, mas arredondado-los da mesma forma em ambos os casos.
date('Y-m-d\TH:i:s', $time / 1000) . sprintf('.%03dZ', substr($time, 10));
?
$time
já estiver em milissegundos, sim, isso funcionaria tecnicamente. Não ameis o substr
corte, mas eu acho que ele iria trabalhar para datas entre 2001 e 2286.
$time
é MS, mas e 2286
, quero dizer, por que você pensa assim e como seria possível escapar dela?
Isso é baseado na resposta do ArchCodeMonkey.
Mas simplificado, se você quiser algo rápido que funcione.
function DateTime_us_utc(){
return DateTime::createFromFormat('U.u', number_format(microtime(true), 6, '.', ''));
}
function DateTime_us(){
$now = DateTime_us_utc();
return $now->setTimeZone(new DateTimeZone(date_default_timezone_get()));
}
Então para mim então
$now = DateTime_us();
$now->format("m-d-Y H:i:s.u");
A partir do PHP 7.1, você pode simplesmente fazer isso:
$date = new DateTime( "NOW" );
echo $date->format( "m-d-Y H:i:s.u" );
Será exibido como:
04-11-2018 10:54:01.321688
A documentação diz o seguinte:
Microssegundos (adicionado no PHP 5.2.2). Observe que date () sempre gerará 000000, pois leva um parâmetro inteiro, enquanto DateTime :: format () oferece suporte a microssegundos.
Ou seja, use DateTime em seu lugar.
new DateTime()
também retornará 0000 para u. Mas se você fornecer um tempo de precisão de microssegundos ao instanciá-lo, ele funcionará bem.
new DateTime( 'Y-m-d H:i:s.'.$micro);
Com o PHP 7.0+ agora aqui, você pode fazer o seguinte:
$dateString = substr($millseconds_go_here,0,10);
$drawDate = new \DateTime(Date('Y-m-d H:i',$dateString));
$drawDate->setTimezone(new \DateTimeZone('UTC'));
Isso faz o seguinte em ordem:
Date()
controlar a data.DateTime()
pode então permitir que você modifique o fuso horário em que você está, mas certifique-se de que date_default_timezone_set("Timezone");
esteja definido antes de usar DateTime()
funções e classes.DateTime()
esteja no fuso horário correto quando as classes ou funções forem usadas.se estiver usando Carbon, você pode usar a especificação definida "RFC3339_EXTENDED". ou personalize-o.
Carbon::RFC3339_EXTENDED = 'Y-m-d\TH:i:s.vP';
Com base na resposta de @ArchCodeMonkey.
Se você tiver, declare(strict_types=1)
você deve lançar o segundo argumento para string
Eu escolhi algumas maneiras diferentes:
1) microtime + sscanf + data:
sscanf(microtime(), '0.%6s00 %s', $usec, $sec);
$date = date('Y-m-d H:i:s.', $sec) . $usec;
Não sei por que microtime () retorna 10 caracteres (0.dddddd00) para a parte de microssegundos, mas talvez alguém possa me dizer?
$start_ts = microtime(true); for($i = 0; $i < 10000000; $i++) { sscanf(microtime(), '0.%6s00 %s', $usec, $sec); $date = date('Y-m-d H:i:s.', $sec) . $usec; } var_dump((microtime(true) - $start_ts)*1000 . ' ms');
string(18) "22372.335910797 ms" // macOS PHP 5.6.30
string(18) "16772.964000702 ms" // Linux PHP 5.4.16
string(18) "10382.229089737 ms" // Linux PHP 7.3.11 (same linux box as above)
2) DateTime :: createFromFormat + Datetime-> format:
$now = new DateTime('NOW');
$date = $now->format('Y-m-d H:i:s.u');
não funciona no PHP 5.x ...
$start_ts = microtime(true); for($i = 0; $i < 10000000; $i++) { $now = new DateTime('NOW'); $date = $now->format('Y-m-d H:i:s.u'); } var_dump((microtime(true) - $start_ts)*1000 . ' ms');
string(18) "45801.825046539 ms" // macOS PHP 5.6.30 (ms not working)
string(18) "21180.155038834 ms" // Linux PHP 5.4.16 (ms not working)
string(18) "11879.796028137 ms" // Linux PHP 7.3.11 (same linux box as above)
3) gettimeofday + date:
$time = gettimeofday();
$date = date('Y-m-d H:i:s.', $time['sec']) . $time['usec'];
-
$start_ts = microtime(true); for($i = 0; $i < 10000000; $i++) { $time = gettimeofday(); $date = date('Y-m-d H:i:s.', $time['sec']) . $time['usec']; } var_dump((microtime(true) - $start_ts)*1000 . ' ms');
string(18) "23706.788063049 ms" // macOS PHP 5.6.30
string(18) "14984.534025192 ms" // Linux PHP 5.4.16
string(18) "7799.1390228271 ms" // Linux PHP 7.3.11 (same linux box as above)
4) microtime + number_format + DateTime :: createFromFormat + DateTime-> format:
$now = DateTime::createFromFormat('U.u', number_format(microtime(true), 6, '.', ''));
$date = $now->format('Y-m-d H:i:s.u');
-
$start_ts = microtime(true); for($i = 0; $i < 10000000; $i++) { $now = DateTime::createFromFormat('U.u', number_format(microtime(true), 6, '.', '')); $date = $now->format('Y-m-d H:i:s.u'); } var_dump((microtime(true) - $start_ts)*1000 . ' ms');
string(18) "83326.496124268 ms" // macOS PHP 5.6.30
string(18) "61982.603788376 ms" // Linux PHP 5.4.16
string(16) "19107.1870327 ms" // Linux PHP 7.3.11 (same linux box as above)
5) microtime + sprintf + DateTime :: createFromFormat + DateTime-> format:
$now = DateTime::createFromFormat('U.u', sprintf('%.6f', microtime(true)));
$date = $now->format('Y-m-d H:i:s.u');
-
$start_ts = microtime(true); for($i = 0; $i < 10000000; $i++) { $now = DateTime::createFromFormat('U.u', sprintf('%.6f', microtime(true))); $date = $now->format('Y-m-d H:i:s.u'); } var_dump((microtime(true) - $start_ts)*1000 . ' ms');
string(18) "79387.331962585 ms" // macOS PHP 5.6.30
string(18) "60734.437942505 ms" // Linux PHP 5.4.16
string(18) "18594.941139221 ms" // Linux PHP 7.3.11 (same linux box as above)