繁体   English   中英

Java将字符串yyyy-MM-dd HH:mm:ss转换为加拿大/东部时区的时间戳

[英]Java Convert String yyyy-MM-dd HH:mm:ss to timestamp of Canada/Eastern timezone

我必须使用TimeZone获取DateTime,然后从该DateTime获取时间戳

我的代码如下:

DateFormat formatter = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
Date dt = new Date();
String currentTime = formatter.format(dt);
System.out.println("currentTime>>>>" + currentTime);

DateFormat format = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
format.setTimeZone(TimeZone.getTimeZone("Canada/Eastern"));
Date parsedDate = format.parse(currentTime);
System.out.println("parsedDate>>>>" + parsedDate);
Timestamp timestamp = new Timestamp(parsedDate.getTime());
System.out.println("timestamp>>>>>>" + timestamp);

问题是我在时间戳中没有得到正确的加拿大/东部时区的日期时间。

我正在下面的时间

currentTime>>>>2016-11-09 15:17:09
parsedDate>>>>Thu Nov 10 01:47:09 IST 2016
timestamp>>>>>>2016-11-10 01:47:09.0

Indian time is correct : 2016-11-09 15:17:09
When I parse it to Canada/Eastern it shows : Thu Nov 10 01:47:09 IST 2016

但是加拿大东部时间是04:50:21 EST Wednesday, 9 November 2016东部时间04:50:21 EST Wednesday, 9 November 2016

我将Java与Eclipse Mars 1结合使用。

时间戳是唯一的,并且在所有时区中的每个地方都相同,这是新的Date()的值,以毫秒为单位。 您在这里寻找的是给定时间戳的格式化时间(上例中的dt)。

Date dt = new Date();
DateFormat format = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");

System.out.println("IST time: " + format.format(dt));

format.setTimeZone(TimeZone.getTimeZone("Canada/Eastern"));

String parsedDate = format.format(dt);

System.out.println("Canada Time: " + parsedDate);

输出:IST时间:2016-11-09 16:33:22加拿大时间:2016-11-09 06:03:22

TL;博士

Instant.now()
       .atZone( ZoneId.of( "America/Toronto" ) )

没有解析! 解析调整时区。

避免麻烦的旧类: java.text.SimpleDateFormatjava.util.Datejava.util.TimeZone

java.time

您正在使用麻烦的旧日期时间类(现在已遗留),由java.time类取代。

Instant

Instant类以UTC表示时间轴上的时刻,分辨率为纳秒 (最多十进制的九(9)位数字)。

Instant instant = Instant.now();

2016-11-10T04:52:02.586Z

时区

您可以调整该Instant通过施加到一个时区ZoneId获得ZonedDateTime

解析,以此来调整时区! 也许您正在将日期时间对象与可能表示其值的字符串进行混合。 日期时间对象可以生成一个字符串,并且可以解析一个字符串,但是该字符串始终与日期时间对象是不同的且分开的。

continent/region的格式指定正确的时区名称 ,例如America/MontrealAfrica/CasablancaPacific/Auckland 切勿使用ESTIST等3-4个字母的缩写,因为它们不是真实的时区,不是标准化的,甚至不是唯一的(!)。

此外,您的Canada/Eastern区域实际上只是America/Toronto的真实区域的别名。

ZoneId z = ZoneId.of( "America/Toronto" );
ZonedDateTime zdt = instant.atZone( z );

2016-11-09T23:52:02.586-05:00 [美国/多伦多]

您也可以调整到印度时间。

ZoneId zKolkata = ZoneId.of( "Asia/Kolkata" );
ZonedDateTime zdtKolkata = instant.atZone( zKolkata );

2016-11-10T10:22:02.586 + 05:30 [亚/加尔各答]

转储到控制台。

System.out.println( "instant: " + instant );
System.out.println( "zdt: " + zdt );
System.out.println( "zdtKolkata: " + zdtKolkata );

即时:2016-11-10T04:52:02.586Z

zdt:2016-11-09T23:52:02.586-05:00 [美国/多伦多]

zdtKolkata:2016-11-10T10:22:02.586 + 05:30 [亚洲/加尔各答]

请参阅IdeOne.com中的实时代码

数据库

通过Timestamp我假设您的意思是java.sql.Timestamp 如果您具有符合JDBC 4.2或更高版本的JDBC驱动程序,则该类现在已被java.time类淘汰。 只需将Instant对象传递给PreparedStatement::setObject 通过ResultSet::getObject获取。

myPreparedStatement.setObject( … , instant );

如果您的JDBC驱动程序不符合要求,请退回转换为java.sql.Timestamp 但是,仅在与数据库对话时,尽量减少使用该类。 立即转换回java.time。 不要尝试使用Timestamp业务逻辑。

java.sql.Timestamp ts = java.sql.Timestamp.from( instant );

关于java.time

java.time框架内置于Java 8及更高版本中。 这些类取代了麻烦的旧的旧式日期时间类,例如java.util.DateCalendarSimpleDateFormat

现在处于维护模式Joda-Time项目建议迁移到java.time。

要了解更多信息,请参见Oracle教程 并在Stack Overflow中搜索许多示例和说明。 规格为JSR 310

在哪里获取java.time类?

  • Java SE 8SE 9及更高版本
    • 内置。
    • 标准Java API的一部分,具有捆绑的实现。
    • Java 9添加了一些次要功能和修复。
  • Java SE 6SE 7
    • java.time的许多功能在ThreeTen- Backport中都被反向移植到Java 6和7。
  • Android的

ThreeTen-Extra项目使用其他类扩展了java.time。 该项目为将来可能在java.time中添加内容提供了一个试验场。 您可以在这里找到一些有用的类,比如IntervalYearWeekYearQuarter ,和更多

您可以基于格林尼治标准时间设置时区。 我们知道加拿大时间是GMT-5 ,因此您可以这样获取当前加拿大时间:

    TimeZone tz = TimeZone.getTimeZone("GMT-5");
    Calendar c = Calendar.getInstance(tz);
    SimpleDateFormat dateFormat = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss", Locale.CANADA);

    dateFormat.setTimeZone(tz);

    System.out.println(dateFormat.format(c.getTime()));

输出:2016-11-09 06:08:47

您需要显式使用DateFormat.setTimeZone()在所需的时区中打印日期。 如果不这样做,则c.getTime()结果将是您区域的当前时间。

Timestamp在Java中没有时区,它仅表示自参考点(纪元)以来经过的毫秒数的时刻。

因此在我看来,您希望您的时间戳指向当前时刻,该时刻的编写非常简单:

//with Java 8
Timestamp ts = Timestamp.from(Instant.now());

//or prior to Java 8:
Timestamp ts = new Timestamp(new Date().getTime());

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM