在 JavaScript 中将日期转换为另一个时区

IT技术 javascript timezone
2021-01-28 21:01:07

我正在寻找一种将一个时区中的日期转换为另一个时区的函数。

它需要两个参数,

  • 日期(格式为“2012/04/10 10:10:30 +0000”)
  • 时区字符串(“亚洲/雅加达”)

时区字符串在http://en.wikipedia.org/wiki/Zone.tab 中描述

是否有捷径可寻?

6个回答

这是单线:

function convertTZ(date, tzString) {
    return new Date((typeof date === "string" ? new Date(date) : date).toLocaleString("en-US", {timeZone: tzString}));   
}

// usage: Asia/Jakarta is GMT+7
convertTZ("2012/04/20 10:10:30 +0000", "Asia/Jakarta") // Tue Apr 20 2012 17:10:30 GMT+0700 (Western Indonesia Time)

// Resulting value is regular Date() object
const convertedDate = convertTZ("2012/04/20 10:10:30 +0000", "Asia/Jakarta") 
convertedDate.getHours(); // 17

// Bonus: You can also put Date object to first arg
const date = new Date()
convertTZ(date, "Asia/Jakarta") // current date-time in jakarta.

   

这是MDN 参考

注意警告:上面的函数依赖于解析 toLocaleString 结果来工作,它是在en-USlocale 中格式化的日期字符串,例如"4/20/2012, 5:10:30 PM". 每个浏览器可能不接受en-US格式化的日期字符串到它的 Date 构造函数,它可能会返回意外的结果(它可能会忽略夏令时)。

目前所有现代浏览器都接受这种格式并正确计算夏令时,它可能不适用于旧浏览器和/或异国浏览器。

旁注:如果现代浏览器有 toLocaleDate 函数会很棒,所以我们不必使用这个 hacky 解决方法。

我改变了这个答案,因为这是不使用任何库的正确和标准方法。
2021-03-12 21:01:07
@MattJohnson 那么你不能使用 getHour() 或这样的方法
2021-03-16 21:01:07
MDN 文档明确指出,在所有实现中唯一需要识别的时区是 UTC。( stackoverflow.com/questions/10087819/... ) 单击 IE11 中的 [运行代码片段] 按钮会产生错误。
2021-03-20 21:01:07
这是一种有缺陷的方法。它不解析 OP 格式,它依赖于浏览器解析不需要解析的格式,它可能会错误地应用夏令时偏移量,并且将时间戳显示为 UTC,但并非如此。.toLocaleString(...)部分是确定的,其余不是。
2021-03-28 21:01:07
这个答案显示正确地将时区传递给toLocaleString,但是它非常错误地显示将该字符串传递回Date构造函数。那是自找麻烦。日期字符串解析器不需要接受特定于区域设置的格式,并且输入将被视为在本地时区中。不要那样做。只需使用第一次toLocalString调用的字符串输出
2021-04-08 21:01:07

对于moment.js用户,您现在可以使用moment-timezone使用它,您的函数将如下所示:

function toTimeZone(time, zone) {
    var format = 'YYYY/MM/DD HH:mm:ss ZZ';
    return moment(time, format).tz(zone).format(format);
}
是不是“返回时刻(时间)。tz(区域)。格式(格式);” ? 您在代码中给出的那个有我“无效日期”错误。
2021-03-10 21:01:07
无法在浏览器中加载 Moment.js。好难过:(
2021-03-15 21:01:07
我不确定如何添加新时区,文档对我没有帮助。我只是一个程序员,不是时间专家!
2021-03-20 21:01:07
如果您对使用 tz 数据库的副本向浏览器发送 180K 不满意,并且可以忍受旧浏览器上当前时区的退化,请使用Date.prototype.toLocaleString.
2021-03-25 21:01:07
这里的问题是这不返回一个新的 Date 对象,它返回一个字符串。如果那是你想要的,那当然很好。
2021-04-02 21:01:07

大多数浏览器都支持带参数toLocaleString函数,较旧的浏览器通常会忽略这些参数。

const str = new Date().toLocaleString('en-US', { timeZone: 'Asia/Jakarta' });
console.log(str);

在 node.js v8.7.0 中测试成功
2021-03-12 21:01:07
此外,在上述所有浏览器中,它们的格式与jsfiddle.net/pmorch/ptqwmbyu 中显示的完全相同
2021-03-23 21:01:07
它刚刚在 Chrome v59 和 Firefox 桌面 v54 以及 Android v59 上的 Chome 和 iOS 10.3 上的 Safari 10 上运行。它在 IE10 上不起作用。MDN 对 Date.prototype.toLocaleString() 的描述有一个toLocaleStringSupportsLocales()实现,允许您可靠地检查支持。
2021-03-26 21:01:07
Edge 和 chrome 喜欢它:)
2021-03-30 21:01:07
不,这从当前时间开始,但问题是关于转换任意时间(& tz),这些时间非常不同 - Date 只是获取当前系统时间而无法覆盖它。
2021-04-05 21:01:07

无耻地从:http : //www.techrepublic.com/article/convert-the-local-time-to-another-time-zone-with-this-javascript/6016329窃取

/** 
 * function to calculate local time
 * in a different city
 * given the city's UTC offset
 */
function calcTime(city, offset) {

    // create Date object for current location
    var d = new Date();
   
    // get UTC time in msec
    var utc = d.getTime();
   
    // create new Date object for different city
    // using supplied offset
    var nd = new Date(utc + (3600000*offset));
   
    // return time as a string
    return "The local time in " + city + " is " + nd.toLocaleString();
}

此函数可用于通过提供城市/国家名称和偏移值来计算时区值

这个答案已经过时了,应该删除,特别是使用toLocaleString的部分,当它转移到不同的时区时,它可能会报告主机时区。有更好的方法可以为不同的偏移量手动创建时间戳。
2021-03-10 21:01:07
很好....但我认为他希望根据在城市中传递的信息为他查找偏移量。
2021-03-28 21:01:07
这不考虑夏令时的变化。
2021-03-29 21:01:07
没有回答问题,但回答了我的问题(+1)
2021-04-01 21:01:07
那个“3600000”简直要了我的命!在输入中,tz 应该以小时为单位给出!而且,应该减去。所以,如果你通过: var d=new Date calcTime('', d.getTimezoneOffset() / 60 ); 它应该同时回馈。
2021-04-04 21:01:07

好的,找到了!

我正在使用timezone-js这是代码:

var dt = new timezoneJS.Date("2012/04/10 10:10:30 +0000", 'Europe/London');
dt.setTimezone("Asia/Jakarta");

console.debug(dt); //return formatted date-time in asia/jakarta
我不得不投反对票,timezone-js 不支持 DST 并且它没有在它的自述文件中宣传它,这对于寻找它的人来说是一个糟糕的提示。请参阅:github.com/mde/timezone-js/issues/51以及许多其他已提交但似乎未得到修复的问题。
2021-03-13 21:01:07
@Marabunta,看起来像时区(Brian Di Palma 的回答)支持夏令时github.com/moment/moment-timezone/issues/21
2021-03-25 21:01:07
不要使用 TimezoneJS,它会因 DST 更改而被窃听。
2021-03-29 21:01:07
@nus 是的,但确实没有客户端时区/日期管理的解决方案......因此,jquery ui datepicker 一直让我发疯。干杯
2021-04-07 21:01:07