簡體   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