[英]Convert joda.time.DateTime to java.sql.Date and retain time zone
我有以下场景:
Calendar
对象的Swing控件 DateTime
对象(joda) java.sql.Date
对象的数据库连接( OraclePreparedStatement
) 我的问题是Calendar
和DateTime
对象正在以GMT(我想要)正确显示日期,但是当我转换为java.sql.Date
以便发送到数据库时,日期将转换为本地时区。
例如:
Calendar
和DateTime
是2012-08-13T23:59:59.000Z(正确的GMT) java.sql.Date
是2012-08-14(本地UTC + 2日期不正确) 下面是我用来进行转换的代码。
DateTime dateGmt = new DateTime(calendarGmt.getTimeInMillis(), DateTimeZone.UTC);
java.sql.Date sqlDate = new java.sql.Date(dateGmt.getMillis());
我不知道如何创建一个java.sql.Date
对象,同时保留正确的时区。 我完全有可能做错误的转换。
一个问题可能是java.sql.Date应该是......
通过在与实例关联的特定时区中将小时,分钟,秒和毫秒设置为零来“标准化”。
......根据文件 。 这意味着,日期时间的时间部分将从java.util.Date或Joda-Time DateTime对象中清除。
正如Gilbert Le Blanc指出的正确答案 ,java.util.Date和java.sql.Date都没有内部时区的概念。 它们存储自Unix 纪元以来的毫秒数。
这些类带来了一个讨厌的技巧 :它们的toString
方法将JVM的默认时区应用于字符串的呈现。 很混乱。 Date
对象没有时区,但当显示为字符串时,您会看到一个时区。
如果您的java.util.Date对象包含自纪元(1970年开始)以来的1344902399000L毫秒数,则表示2012-08-13T23:59:59.000Z
(UTC / GMT)。 但如果您的JVM认为自己在夏令时有效,那么您将看到提前2小时的UTC / GMT: 2012-08-14T01:59:59.000+02:00
在该课程中描述糟糕的字符串格式。 同一时刻在不同的时区有不同的日期意义(13对14),墙上的时钟已经过了午夜。
Joda-Time 2.4库在这里很有帮助。 将java.sql.Date或java.util.Date对象与UTC时区对象一起传递给DateTime构造函数,以获得您正在苦苦挣扎的值的清晰图片。
java.util.Date date = new java.util.Date( 1390276603054L );
DateTime dateTimeUtc = new DateTime( date, DateTimeZone.UTC );
System.out.println( "dateTimeUtc: " + dateTimeUtc );
跑的时候......
2014-01-21T03:56:43.054Z
将另一个方向从Joda-Time转换为java.util.Date ...
java.util.Date date = myDateTime.toDate();
将另一个方向从Joda-Time转换为java.sql.Date ...
java.sql.Date date = new java.sql.Date( myDateTime.getMillis() );
Joda-Time项目现在处于维护模式,团队建议迁移到java.time类。
java.util.Date
的等价物是Instant
。 Instant
类表示UTC时间轴上的一个时刻,分辨率为纳秒 (最多九(9)位小数)。
Instant instant = Instant.ofEpochMilli( 1390276603054L );
应用时区ZoneId
生成ZonedDateTime
,类似于java.util.Calendar
和Joda-Time DateTime
。
ZoneId z = ZoneId.of( "Europe/Kaliningrad" );
ZonedDateTime zdt = instant.atZone( z );
现在提取一个仅限日期的值,即ZonedDateTime
的日期部分,作为LocalDate
。 LocalDate
类表示没有时间且没有时区的仅日期值。 因此, LocalDate
是java.sql.Date
假装的:仅限日期的值。
LocalDate localDate = zdt.toLocalDate() ;
在JDBC 4.2及更高版本中,您可以通过PreparedStatement::setObject
和ResultSet::getObject
直接将java.time类型与兼容的驱动程序一起使用。
myPreparedStatement.setObject( … , localDate );
…和…
LocalDate ld = myResultSet.getObject( … , LocalDate.class );
对于较旧的不兼容驱动程序,通过使用添加到旧类的新方法简单地转换为/来自LocalDate
的java.sql.Date
对象: toLocalDate
和valueOf( LocalDate )
。
java.sql.Date
的内部表示是自1970年1月1日00:00:00.000 GMT以来经过的毫秒数。
你确定你没有看到toString
问题吗? toGMTString()
方法虽然已经折旧,但仍然存在。
我想你可能需要添加配置文件TIMEZONE = GMT
在Web应用程序中,这是在web.xml中定义的
<context-param> <param-name>javax.faces.DATETIMECONVERTER_DEFAULT_TIMEZONE_IS_SYSTEM_TIMEZONE</param-name> <param-value>true</param-value> </context-param>
问候
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.