5

Leap SecondsDateTimeでいくつかの計算を行いたかったのですが、意味がわからなかったため、かなり早く停止しました。DateTime

### June 30, 2012 at 23:59:60 UTC ###

$leap = new DateTime('2012-06-30T23:59:60UTC');
var_export($leap);

出力:

DateTime::__set_state(array(
   'date' => '2012-07-01 00:00:00',
   'timezone_type' => 3,
   'timezone' => 'UTC',
))

DateTime昨年のその UTC 閏秒を作成できません(また、私が試した他の閏秒も作成できません)。DateTimeうるう秒をサポートするかどうか疑問に思った.UTCをサポートしていると思ったが、おそらくうるう秒をサポートしていないので、GMTのみをサポートしている

4

2 に答える 2

3

UNIX 時間はうるう秒を無視します。関係する限り、毎日は正確に 86,400 秒で構成されており、時間はたまたま 1 秒をスキップしたり繰り返したりします。(これは主に、うるう秒が事前に完全にスケジュールされていないために必要です。うるう秒が UNIX 時間でカウントされた場合、UNIX 時間と人間が読み取れる日付/時刻の間の「マッピング」は、うるう秒が発表されると予期せず変更されます。 .)

その日付/時刻プリミティブはすべて UNIX 時間に基づいているため、PHP はうるう秒を簡単に表すこともできません。それらは実質的に見えません。

于 2013-01-08T03:53:48.917 に答える
1

これは完全な答えではありませんが、少なくともそれは何かです。

ここには、次の 2 つの問題が考えられます。

  1. ircmaxell が述べたように、PHP はタイムゾーン操作ビット内のどこかでうるう秒を消費している可能性がありますが、さらに調査が必要です。
  2. しかし個人的には、PHP が数秒の「オーバーフロー」を数分に「修正」していると期待しています。DateTimeコンストラクターは、指定された引数を を処理するのと同じコードに渡します。このコードはstrtotime、完全に偽の日付 (たとえば 2 月 31 日) を取得し、意味のあるものに変換することでよく知られています。

ドキュメントでのうるう秒への唯一の参照は次のstrptimeとおりです。

「tm_sec」にはうるう秒が含まれます (現在は年に 2 秒まで)。

たとえば、PHP の対話型プロンプトから省略されます。

php > $eviler_format = '%Y-%m-%d %H:%M:%S %z';
php > $evil = '2012-12-31 23:59:59 +0000';
php > var_dump(strptime($evil, $eviler_format));
array(9) {
  'tm_sec' =>
  int(59) // ...
}
php > $evil = '2012-12-31 23:59:60 +0000';
php > var_dump(strptime($evil, $eviler_format));
array(9) {
  'tm_sec' =>
  int(60) // ...
}
php > $evil = '2012-12-31 23:59:61 +0000';
php > var_dump(strptime($evil, $eviler_format));
array(9) {
  'tm_sec' =>
  int(61) // ...
}
php > $evil = '2012-12-31 23:59:62 +0000';
php > var_dump(strptime($evil, $eviler_format));
bool(false)

残念ながら、12 月 31 日ではない「うるう秒」も必要です。

php > $evil = '2012-01-07 23:59:61 +0000';
php > var_dump(strptime($evil, $eviler_format));
array(9) {
  'tm_sec' =>
  int(61)
  'tm_min' =>
  int(59)
  'tm_hour' =>
  int(23)
  'tm_mday' =>
  int(7)
  'tm_mon' =>
  int(0)
  'tm_year' =>
  int(112)
  'tm_wday' =>
  int(6)
  'tm_yday' =>
  int(6)
  'unparsed' =>
  string(0) ""
}

または真夜中ではない:

php > $evil = '2012-01-07 08:59:61 +0000';
php > var_dump(strptime($evil, $eviler_format));
array(9) {
  'tm_sec' =>
  int(61)
  'tm_min' =>
  int(59)
  'tm_hour' =>
  int(8)
  'tm_mday' =>
  int(7)
  'tm_mon' =>
  int(0)
  'tm_year' =>
  int(112)
  'tm_wday' =>
  int(6)
  'tm_yday' =>
  int(6)
  'unparsed' =>
  string(0) ""
}

さらに、それはまったく接続さDateTimeれていない完全にプレゼンテーション機能です。数学を行うことはできません。物事の明確な性質を考えると、実際のうるう秒を取得することは現実の世界では不可能です。ここは駄目です。

結論: PHP はうるう秒を考慮していません。サーバーが、それを気にする上流の NTP サーバーと同期されていることを確認してください。最終的には問題ありません。うるう秒に関して第 2 レベルの精度を気にする必要がある場合、PHP はおそらくあなたにとって間違った言語です。

于 2013-01-08T03:30:19.767 に答える