首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >java中不同时区的日期差异

java中不同时区的日期差异
EN

Stack Overflow用户
提问于 2018-03-17 16:31:43
回答 3查看 182关注 0票数 0

我从一个表中实际地构建了一个嵌套的JSON。Json看起来像这样:

代码语言:javascript
复制
{"date":"03-16-2018 06:57:02",
 "details":
    [  
        {  
           "motorstate":0,
           "startTime":"03-16-2018 20:41:57",               
        },
        {  
           "motorstate":0,
           "startTime":"03-16-2018 06:57:02",               
        }
     ]
},
{"date":"03-15-2018 08:08:48",
"details":
   [  
        {  
           "motorstate":0,
           "startTime":"03-16-2018 03:53:30",
        }
   ]
}

如果你看一下上面的例子,第二条记录:

代码语言:javascript
复制
{"date":"03-15-2018 08:08:48",
"details":
   [  
        {  
           "motorstate":0,
           "startTime":"03-16-2018 03:53:30",
        }
   ]
}

日期不匹配。这是因为这里显示的日期是IST格式的,但实际上是以UTC格式存储在我的Google数据存储中的。在UTC,它仍然是03-15-2018,而不是03-16-2018。

我的问题是,除了Java中的UTC之外,我们如何在不同的时区执行日期差异?Date.getTime()方法总是以协调世界时为单位,而不是以本地时区为单位。

EN

回答 3

Stack Overflow用户

发布于 2018-03-17 23:51:50

tl;dr

java中不同时区的

日期差异

代码语言:javascript
复制
Period.between(
    LocalDateTime.parse(
         "03-15-2018 08:08:48" , 
         DateTimeFormatter.ofPattern( “MM-dd-uuuu HH:mm:ss” )
    )
    .atZone( ZoneId.of( ”Asia/Kolkata" )  ) 
    .toLocalDate()
    ,
    LocalDate.now( ZoneId.of( ”Asia/Kolkata" ) )
)

详细信息

现代方法使用java.time类,而不是麻烦的老旧的遗留日期-时间类,如DateCalendar

提示:在将日期时间值序列化为文本时,请避免使用自定义格式模式。仅使用标准ISO 8601格式。

提示:当以文本形式交换日期-时间值时,请始终包括从UTC的偏移量和时区名称的指示器。

首先,将输入字符串解析为LocalDateTime,因为它们缺少任何偏移量或区域的指示。

定义与输入匹配的格式化模式。

代码语言:javascript
复制
DateTimeFormatter f = DateTimeFormatter.ofPattern( “MM-dd-uuuu HH:mm:ss” ) ;

解析。

代码语言:javascript
复制
String input = "03-15-2018 08:08:48" ;
LocalDateTime ldt = LocalDateTime.parse( input , f ) ;

您声称知道这些输入旨在表示印度时间中的某个时刻。应用ZoneId以获取ZonedDateTime

代码语言:javascript
复制
ZoneId z = ZoneId.of( ”Asia/Kolkata" ) ;
ZonedDateTime zdt = ldt.atZone( z ) ;

要获取仅限日期的值,请提取一个LocalDate

代码语言:javascript
复制
LocalDate ld = zdt.toLocalDate() ; 

要将日期之间的增量表示为未附加到时间线的若干年、月和日,请使用Period

代码语言:javascript
复制
Period p = Period.between( ldt , LocalDate.now( z ) ) ;

用于总天数的计数。

代码语言:javascript
复制
long days = ChronoUnit.DAYS.between( start , stop ) ;

关于java.time

框架内置于Java8和更高版本中。这些类取代了麻烦的旧legacy日期时间类,如java.util.DateCalendarSimpleDateFormat

现在在maintenance mode中的项目建议迁移到java.time类。

要了解更多信息,请参阅。和搜索堆栈溢出,以获得许多示例和解释。规范为JSR 310

您可以直接与数据库交换java.time对象。使用与JDBC 4.2或更高版本兼容的JDBC driver。不需要字符串,也不需要java.sql.*类。

从哪里获取java.time类?

  • ,,以及后来内置的
    • 。与implementation.
    • Java 9捆绑在一起的标准Java API的
    • 部分添加了一些次要功能和fixes.

  • 和.

中的

  • 许多java.time功能已向后移植到Java6和7

    • 更高版本的Android捆绑实现的java.time类。
    • 对于较早的Android (<26),项目适配ThreeTen-Backport (如上所述)。请参阅.

项目使用额外的类扩展了java.time。这个项目是未来可能添加到java.time中的试验场。您可能会在这里找到一些有用的类,如IntervalYearWeekYearQuartermore

票数 3
EN

Stack Overflow用户

发布于 2018-03-17 16:51:07

下面的方法会将您的UTC时间返回到当前时区,这对我很有效

代码语言:javascript
复制
  public static Date getLocalDateObjFromUTC(String date, String time) throws ParseException {
    String dateAndTimeInUTC = date + " " + time;
    SimpleDateFormat localDateFormat = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss", Locale.getDefault());
    localDateFormat.setTimeZone(TimeZone.getTimeZone("UTC"));
    Date dateInLocalTimeZone = localDateFormat.parse(dateAndTimeInUTC);
    return dateInLocalTimeZone;
}
票数 0
EN

Stack Overflow用户

发布于 2018-03-17 17:02:54

代码语言:javascript
复制
public String getSummary(String deviceGuid)
{
    Query<com.google.cloud.datastore.Entity> query 
        = Query.newEntityQueryBuilder()
            .setKind("sensordata")
            .setFilter(PropertyFilter.eq("deviceguid", deviceGuid))
            .setOrderBy(OrderBy.desc("startTime"))
            .build();

    QueryResults<com.google.cloud.datastore.Entity> resultList = 
  datastore.run(query);
    if(!resultList.hasNext())
    {           
        log.warning("No record found..");
        return "No record found";
    }

    com.google.cloud.datastore.Entity e =null;
    com.google.cloud.datastore.Entity pe =null;

    SensorDataOut sensorDataOut = new SensorDataOut();
    SensorSummaryDataOut summary = new SensorSummaryDataOut();
    TotalSummaryDataOut totalSummary = new TotalSummaryDataOut();


    Calendar calendar = Calendar.getInstance();
    calendar.setTimeZone(TimeZone.getTimeZone("IST"));

    Calendar calendar1 = Calendar.getInstance();
    calendar1.setTimeZone(TimeZone.getTimeZone("IST"));


    SimpleDateFormat sdf = new SimpleDateFormat("MM-dd-yyyy HH:mm:ss");
    sdf.setTimeZone(TimeZone.getTimeZone("IST"));

    SimpleDateFormat sdf1 = new SimpleDateFormat("MM-dd-yyyy");
    //sdf.setTimeZone(TimeZone.getTimeZone("IST"));



    long stopTime;
    long startTime;
    long pStartTime;
    long diffTime;
    long diffDay;
    Date pDateWithoutTime;
    Date eDateWithoutTime;

    while(resultList.hasNext())
    {
        e = resultList.next();

        startTime  = (e.contains("startTime"))?e.getTimestamp("startTime").toSqlTimestamp().getTime():0;
        stopTime  = (e.contains("stopTime"))?e.getTimestamp("stopTime").toSqlTimestamp().getTime():0;   
        //log.info("Start Date : " + e.getTimestamp("startTime").toString() + " - " +  String.valueOf(startTime));
        //log.info("Stop Date : " + e.getTimestamp("stopTime").toString() + " - " + String.valueOf(stopTime));
        //log.info("Usage Volume :" + String.valueOf(e.getLong("usageVolume")));

        sensorDataOut = new SensorDataOut();

        calendar.setTimeInMillis(stopTime);                                             
        sensorDataOut.stopTime = sdf.format(calendar.getTime());

        calendar.setTimeInMillis(startTime);                                    
        sensorDataOut.startTime = sdf.format(calendar.getTime());


        sensorDataOut.motorstate    = (e.contains("motorstate"))?(int)e.getLong("motorstate"):-1;
        sensorDataOut.startVolume   = (e.contains("startVolume"))?(int)e.getLong("startVolume"):-1;
        sensorDataOut.stopVolume    = (e.contains("stopVolume"))?(int)e.getLong("stopVolume"):-1;
        sensorDataOut.usageTime     = (e.contains("usageTime"))?e.getLong("usageTime"):-1;
        sensorDataOut.usageVolume   = (e.contains("usageVolume"))?(int)e.getLong("usageVolume"):-1;

        if(pe!=null)
        {               
            //Get the date difference in terms of days. If it is same day then add the volume consumed
            pStartTime= pe.getTimestamp("startTime").toSqlTimestamp().getTime();
            try{
                calendar.setTimeInMillis(pStartTime);
                pDateWithoutTime = sdf1.parse(sdf1.format(calendar.getTime()));

                calendar1.setTimeInMillis(e.getTimestamp("startTime").toSqlTimestamp().getTime());
                eDateWithoutTime = sdf1.parse(sdf1.format(calendar1.getTime()));    


            }
            catch(Exception ex){
                log.info("Exception while parsing date");
                continue;
            }


            diffTime = Math.abs(pDateWithoutTime.getTime() - eDateWithoutTime.getTime());
            diffDay = TimeUnit.DAYS.convert(diffTime, TimeUnit.MILLISECONDS);


            //log.info("pDateWithoutTime: " + pDateWithoutTime +  ", eDateWithoutTime: " + eDateWithoutTime + ", consumedVolume: " 
            //          + sensorDataOut.usageVolume;


            if(diffDay!=0) //If not same day
            {
                totalSummary.totVolume = totalSummary.totVolume + summary.totVolume;
                totalSummary.totDuration = totalSummary.totDuration + summary.totDuration;                  
                totalSummary.details.add(summary);
                summary = new SensorSummaryDataOut();                   
            }

        }

        summary.date = sensorDataOut.startTime;         
        summary.totVolume = summary.totVolume + sensorDataOut.usageVolume;
        summary.totDuration = summary.totDuration + sensorDataOut.usageTime;            
        summary.details.add(sensorDataOut);

        pe = e;
    }

    if(summary.details.size()>0)
    {
        totalSummary.totVolume = totalSummary.totVolume + summary.totVolume;
        totalSummary.totDuration = totalSummary.totDuration + summary.totDuration;                  
        totalSummary.details.add(summary);
        summary = new SensorSummaryDataOut();                   
    }

    totalSummary.avgVolume = totalSummary.totVolume/totalSummary.details.size();
    totalSummary.deviceguid = deviceGuid;

    String json = "";
    Gson gson = new Gson();
    json = gson.toJson(totalSummary);
    return json;

} //End of Function
票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/49334040

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档