【问题标题】:Java time load Date of a country and convert to localtime [duplicate]Java时间加载一个国家/地区的日期并转换为本地时间[重复]
【发布时间】:2015-03-13 17:21:17
【问题描述】:

我需要在 java 变量中加载一个日期,例如:“14-03-2015 14:00:00”。但是那个日期是格林威治标准时间+4

我想将其转换为我的当地时间,即 GMT +1

我已经看到很多转换来获取一个国家/地区的当地时间。例如,此代码显示墨尔本和马德里的本地日期,但不是我正在搜索的。

DateTime dt = new DateTime(org.joda.time.DateTimeZone.forID("Australia/Melbourne"));
DateTimeZone dtZone = DateTimeZone.forID("Europe/Madrid");
DateTime dtus = dt.withZone(dtZone);

提前非常感谢;)

【问题讨论】:

  • 那么,您搜索的是什么?你期望输出是什么,而这段代码给你的是什么?
  • 当时并不清楚您寻找什么,因为该代码会从一个时区转换为另一个时区。您需要在那个时区解析它的问题吗?请说得更具体一些,否则很难为您提供帮助。
  • 我需要在 java 变量中加载 GMT +4 的日期并将其转换为我的本地时间,即 GMT +1

标签: java time jodatime java-time


【解决方案1】:

无论时区是什么,java.util.Date 对象(不是 JodaTime)都是相同的。在幕后,它总是格林威治标准时间。您只需要在解析(创建 Date 对象)或打印时担心时区。

使用时区设置为 +4 的 SimpleDateFormat 来解析和创建您的 Date 对象。 使用时区设置为 +1 的不同 SimpleDateFormat 来格式化相同的 Date 对象以进行打印。

您可以在 SimpleDateFormat 上调用 setTimeZone 或使用包含时区的格式字符串构造它。 http://docs.oracle.com/javase/7/docs/api/java/text/DateFormat.html#setTimeZone(java.util.TimeZone)

【讨论】:

    【解决方案2】:

    你不需要使用 Joda 时间,用核心 Java 库计算真的很容易。仅计算时差是不够的,应考虑夏季和冬季时间的切换。

    应使用 Java 的

    TimeZone#getRawOffsetTimeZone#getDSTSavingsTimeZone#inDaylightTime 方法。使用 TimeZone#getRawOffset 获取 UTC 时间的时间偏移量。请特别注意此方法,因为这不会返回夏令时。使用 TimeZone#getDSTSavings 获取以毫秒为单位的日光偏移时间。最后使用 TimeZone#inDaylightTime 检查时间是否在 DST。

    这是完整的代码;

            TimeZone timeZoneMelbourne = TimeZone.getTimeZone("Australia/Melbourne");
            TimeZone timeZoneMadrid = TimeZone.getTimeZone("Europe/Madrid");
    
            System.out.println("timeZoneMelbourne.getRawOffset() -> " + timeZoneMelbourne.getRawOffset());
            System.out.println("timeZoneMadrid.getRawOffset() -> " + timeZoneMadrid.getRawOffset());
            System.out.println("timeZoneMelbourne.getDSTSavings() -> " + timeZoneMelbourne.getDSTSavings());
            System.out.println("timeZoneMadrid.getDSTSavings() -> " + timeZoneMadrid.getDSTSavings());
    
            Calendar c = Calendar.getInstance();
            c.set(Calendar.YEAR, 2015);
            c.set(Calendar.MONTH, 2);
            c.set(Calendar.DAY_OF_MONTH, 13);
    
            c.set(Calendar.HOUR_OF_DAY, 20);
            c.set(Calendar.MINUTE, 0);
            c.set(Calendar.SECOND, 0);
    
    
            int timeDiff =  timeZoneMadrid.getRawOffset() - timeZoneMelbourne.getRawOffset();
            int madridDST = 0;
            int melbourneDST = 0;
    
            if(timeZoneMadrid.inDaylightTime(c.getTime()))
            {
                madridDST = timeZoneMadrid.getDSTSavings();
                System.out.println("timeZoneMadrid#inDaylightTime -> " + madridDST);
            }
    
            if(timeZoneMelbourne.inDaylightTime(c.getTime()))
            {
                melbourneDST += timeZoneMelbourne.getDSTSavings();
                System.out.println("timeZoneMelbourne#inDaylightTime -> " + melbourneDST);
            }
    
            timeDiff = timeDiff - melbourneDST + madridDST;
    
            System.out.println("total timeDiff -> " +timeDiff);
    
    
            System.out.println("timeZoneMelbourne -> " +c.getTime());
    
            c.add(Calendar.MILLISECOND,  timeDiff);
    
            System.out.println("timeZoneMadrid -> " +c.getTime());
    

    代码的输出;

    timeZoneMelbourne.getRawOffset() -> 36000000
    
    timeZoneMadrid.getRawOffset() -> 3600000
    
    timeZoneMelbourne.getDSTSavings() -> 3600000
    
    timeZoneMadrid.getDSTSavings() -> 3600000
    
    timeZoneMelbourne#inDaylightTime -> 3600000
    
    timeDiff -> -36000000
    
    timeZoneMelbourne -> Fri Mar 13 20:00:00 EET 2015
    
    timeZoneMadrid -> Fri Mar 13 10:00:00 EET 2015
    

    检查this 的正确性。 3 月 13 日有 10 小时的时差。

    让我们测试 6 月 13 日的代码,这是马德里的夏季时间。此外,夏季和冬季时间之间存在转换。

    这是代码的输出;

    timeZoneMelbourne.getRawOffset() -> 36000000
    
    timeZoneMadrid.getRawOffset() -> 3600000
    
    timeZoneMelbourne.getDSTSavings() -> 3600000
    
    timeZoneMadrid.getDSTSavings() -> 3600000
    
    timeZoneMadrid#inDaylightTime -> 3600000
    
    total timeDiff -> -28800000
    
    timeZoneMelbourne -> Sat Jun 13 20:00:00 EEST 2015
    
    timeZoneMadrid -> Sat Jun 13 12:00:00 EEST 2015
    

    您可以在this查看计算的正确性

    此外,我完全同意@dimo414。最佳实践是使用 Joda 时间进行日期和时间操作。

    这是 Joda 代码;

        Calendar c = Calendar.getInstance();
        c.set(Calendar.YEAR, 2015);
        c.set(Calendar.MONTH, 5);
        c.set(Calendar.DAY_OF_MONTH, 13);
    
        c.set(Calendar.HOUR_OF_DAY, 20);
        c.set(Calendar.MINUTE, 0);
        c.set(Calendar.SECOND, 0);
    
        LocalDateTime dateTime = new LocalDateTime(c.getTime()); 
        DateTime srcDateTime =  dateTime.toDateTime(DateTimeZone.forID("Australia/Melbourne"));
        DateTime dstDateTime = srcDateTime.withZone(DateTimeZone.forID("Europe/Madrid"));
        Date madridTime =dstDateTime.toLocalDateTime().toDateTime().toDate();
    
    
        System.out.println("Melbourne Time -> "+srcDateTime.toDateTime());
        System.out.println("Madrid Time -> "+madridTime);
    

    另见;

    TimeZone#getRawOffset

    TimeZone#getDSTSavings

    TimeZone#inDaylightTime

    【讨论】:

    • 当然,没有 Joda 也可以,但核心 Java 日期实用程序被严重破坏(并在 Java 8 中被替换)。使用 Joda 库进行尽可能多的日期处理是目前公认的最佳实践。
    猜你喜欢
    • 2019-05-29
    • 2016-09-12
    • 1970-01-01
    • 2021-05-02
    • 1970-01-01
    • 2022-12-18
    • 2019-01-14
    • 1970-01-01
    • 2013-06-16
    相关资源
    最近更新 更多