javascript错误地确定夏令时时间线 - 2006年的一个例子

vee*_*ain 6 javascript php windows unix-timestamp dst

我在javascript new Date()对象上阅读了许多关于夏令时时间线的 StackOverflow问题- 就像它们被越过时一样.但是,我还没有看到关于这个特定问题的答案,或者在仍然依赖 'unix time'的情况下解决它的方法.

我个人选择通过将javascript日期作为日期传递给我的PHP代码而不是unix时间来解决此问题.然而,唠叨的问题仍然存在!我已经在IE8,Chrome和FF上确认了这种行为,所以我假设它会对你的行为相同.(更新: OSX用户可能无法生成此行为)

我的研究; 对我的问题最近的问题:

  • 该用户正在处理DST更改周围的特定时间.
  • 该用户担心时间的呈现取决于用户的时区.该页面上接受的答案提到getTimezoneOffset"片状",这使我无法深入研究.
  • 请参阅下面的答案,了解其他一些有很多见解的问题

我已经在2006年11月1日左右生成了测试场景.根据您所在的时区,这可能会或可能不会对您有所帮助.如果我正确理解了javascript方面,您需要将PC的时钟同步到

东部时间(美国和加拿大)并选中"自动调整夏令时的时钟".

我将这个实验基于PHP的"印第安纳波利斯"时区.我的javascript结果,当我发现2006年11月1日的unix时间与PHP生成的时间相差一小时(3600秒).根据这个页面(谢谢乔恩!)javascript是错误的.

这两种语言的结果" 于2006年6月11日重新达成协议!

这和其他的研究使我相信,得到的Javascript的历史错误,选择了错误的周日"依傍"了DST的 - 从而导致我看到的差异.

我试图尽可能地简化这个,但仍然有相当多的齿轮在运动.

1)这是PHP代码和输出,显示直到11/01/2006日期之前的CORRECT毫秒数.

date_default_timezone_set("America/Indiana/Indianapolis");
echo "Unixtime for November 1, 2006 is: ".strtotime("11/01/2006")."\n";
echo "Unixtime for November 6, 2006 is: ".strtotime("11/06/2006");
Run Code Online (Sandbox Code Playgroud)

结果是:

Unixtime for November 1, 2006 is: 1162357200 (where the disagreement lies)
Unixtime for November 6, 2006 is: 1162789200
Run Code Online (Sandbox Code Playgroud)

它们都基于GMT-0500.

2)在Javascript中,(请参阅我的jsfiddle**),我调用new Date然后getTime()就这样(并删除毫秒):

new Date("2006/11/01").getTime()/1000
new Date("2006/11/06").getTime()/1000
Run Code Online (Sandbox Code Playgroud)

这会生成值

1162353600 <-- PHP outputs: 1162357200
1162789200 <-- the same as PHP for '2006/11/06'; congruence is restored
Run Code Online (Sandbox Code Playgroud)

这是一个差异(2006/11/01)从PHP输出3600秒 - 或一小时.这个值(提前一小时)在我的PHP应用程序中处理时产生了前一天(2006/10/31),这是不可接受的,因为它打破了我的导航向前.(查看我特定场景的更多解释)

在Javascript中输出:Date("2006/11/01")没有调用getTime()清除一些神秘,因为javascript显示它正在使用的偏移量GMT-0400.

我的jsfiddle**实验(也在上面列出)显示了这些结果.

**(您可能需要更改计算机的时区以查看相同的行为).

可能发挥作用的是维基百科2006年是印第安纳州开始使用DST 的第一年.无论如何都是一个奇怪的谜题

由于我已经制定了我的解决方案(通过避免依赖我的javascript中的unix时间)我认为我应该发布这个为后代,并希望有人可能知道如何纠正javascript显示的值.

问题是:如何将PHP和javascript之间的两个'unix time'结果对齐?我很高兴了解DST'线'或一般情况.(我现在假设DST线是问题).

更新:运行Chrome的iMac生成了PHP生成的结果.什么???野生.任何javascript端修复此行为看起来都是一个伟大的事业(或至少是丑陋的).也许这不是一个javascript问题,因为它根据操作系统(或其他因素?)生成正确的答案.

值得注意的是,在这款iMac上我没有强制使用时区,我不确定这款Apple电脑是否会允许它.检查(true)和"自动设置日期和时间"的设置disabled.时区设置为东部夏令时."自动设置时区"框未选中(false)和disabled.

我添加了Windows标签以突出显示它在OSX中似乎不是问题.

更新:根据现场上面链接,我核实,下面所有的日期跨入一个新的GMT在适当的日期(更新小提琴)偏移 -不像2006年的反应是如何停止一周.即,2007年11月4日,2007年GMT-411月5日,它又回来了GMT-5.

  • 2007年3月11日星期日上午2点,星期日,11月4日凌晨2点
  • 2008年3月9日星期日上午2点,星期日,11月2日凌晨2点
  • 2009年3月8日星期日上午2点,星期日,11月1日凌晨2点
  • 2010年3月14日星期日上午2点,星期日,11月7日星期日凌晨2点
  • 2011年3月13日星期日上午2点,星期日,11月6日凌晨2点

最后,如果您知道在2006年将此错误提交到Javascript所依赖的任何时区源的正确渠道,请执行此操作并告诉我相关信息.

Jon*_*eet 7

首先,印第安纳州的时间非常复杂.

但在这种情况下,我认为Javascript是错误的.我的机器上的Javascript输出(设置了时区)是Chrome上的"Wed Nov 01 2006 00:00:00 GMT-0400(Eastern Daylight Time)"和"Wed Nov 1 00:00:00 EDT 2006"在Internet Explorer上 - 但夏令时在2006年10月29日在印第安纳波利斯结束.

.NET的TimeZoneInfo类给出了相同的结果:

// Ignore the daft ID; it really means Eastern time
var zone = TimeZoneInfo.FindSystemTimeZoneById("Eastern Standard Time");
var local = new DateTime(2006, 11, 1);
Console.WriteLine(zone.GetUtcOffset(local));
Run Code Online (Sandbox Code Playgroud)

输出:

-5:00:00
Run Code Online (Sandbox Code Playgroud)

(所以它知道它不是在夏令时.)

同样在Noda Time(我自己的日期和时间库,它使用tzdb数据库):

var zone = DateTimeZone.ForId("America/Indiana/Indianapolis");
var instant = new Instant(1162357200 * NodaConstants.TicksPerSecond);
var zoned = new ZonedDateTime(instant, zone);
Console.WriteLine(zoned);
Run Code Online (Sandbox Code Playgroud)

结果:

Local: 01/11/2006 00:00:00 Offset: -05 Zone: America/Indiana/Indianapolis
Run Code Online (Sandbox Code Playgroud)