Java Joda DateTime到时间戳的转换

Java Joda DateTime到时间戳的转换,java,jodatime,Java,Jodatime,我正试图通过Joda中的DateTimeZone更改Timestamp的值: 对于DateTime,值为:2013-04-13T22:56:27.000+03:00 对于时间戳,值为:2013-04-13 22:56:27.0 时间戳没有时区差异 如何获得正确的时区时间戳? 例如,我想得到“2013-05-13 01:56:27.0” 提前谢谢 编辑:使用MySQL,列类型是TIMESTAMP当然,rs是ResultSet时间(可测量的第四维度)在世界各地是不同的,这是一种常见的误解。时间戳

我正试图通过Joda中的
DateTimeZone
更改
Timestamp
的值:

  • 对于
    DateTime
    ,值为:
    2013-04-13T22:56:27.000+03:00

  • 对于时间戳,值为:
    2013-04-13 22:56:27.0

时间戳
没有时区差异

如何获得正确的时区时间戳? 例如,我想得到“2013-05-13 01:56:27.0”

提前谢谢


编辑:使用MySQL,列类型是
TIMESTAMP
当然,
rs
ResultSet

时间(可测量的第四维度)在世界各地是不同的,这是一种常见的误解。时间戳作为时间中的一个时刻是唯一的。然而,日期会影响我们“看”时间的方式,但实际上它是“一天中的时间”

例如:两个人同时看钟。时间戳是一样的,对吗? 但其中一个在伦敦,中午12:00(格林尼治标准时间,时区偏移量为0),另一个在贝尔格莱德,下午14:00(CET,中欧,现在夏时制,偏移量为+2)

他们的看法不同,但时间是一样的

您可以在中找到更多详细信息。

更新 好的,它不是的副本,但它是毫无意义的,因为您混淆了术语“时间戳=时间(客观)”和“日期[时间]=一天中的时间(主观)”

让我们看一下您的原始问题代码,如下所示:

// Get the "original" value from database.
Timestamp momentFromDB = rs.getTimestamp("anytimestampcolumn");

// Turn it into a Joda DateTime with time zone.
DateTime dt = new DateTime(momentFromDB, DateTimeZone.forID("anytimezone"));

// And then turn it back into a timestamp but "with time zone".
Timestamp ts = new Timestamp(dt.getMillis());
我没有运行此代码,但我确信它将打印
true
,每次打印的毫秒数相同:

System.out.println("momentFromDB == dt : " + (momentFromDB.getTime() == dt.getTimeInMillis());
System.out.println("momentFromDB == ts : " + (momentFromDB.getTime() == ts.getTime()));
System.out.println("dt == ts : " + (dt.getTimeInMillis() == ts.getTime()));

System.out.println("momentFromDB [ms] : " + momentFromDB.getTime());
System.out.println("ts [ms] : " + ts.getTime());
System.out.println("dt [ms] : " + dt.getTimeInMillis());
但正如您所说,将它们打印为字符串将导致“不同”的时间,因为
DateTime
应用时区。这就是为什么“时间”被存储和传输为
时间戳
对象(它基本上包装了
长的
),并显示或输入为
日期[时间]

在你自己的回答中,你人为地增加了一个偏移量,并创造了一个“错误”的时间。 如果您使用该时间戳创建另一个
DateTime
并将其打印出来,它将偏移两次

// Turn it back into a Joda DateTime with time zone.
DateTime dt = new DateTime(ts, DateTimeZone.forID("anytimezone"));
另外,如果你有时间的话,通过复杂的过程,看看它是如何保持时间的(毫秒),以及它是如何打印时间的

JUnit测试作为证明
事实上,这不是一个重复的问题。这就是我在几次之后解决问题的方法:

   int offset = DateTimeZone.forID("anytimezone").getOffset(new DateTime());
这是从所需时区获取偏移量的方法

让我们回到我们的代码,我们从查询结果集中获取时间戳,并将其与时区一起使用来创建日期时间

   DateTime dt = new DateTime(rs.getTimestamp("anytimestampcolumn"),
                         DateTimeZone.forID("anytimezone"));
现在,我们将把偏移量添加到datetime,并从中获取时间戳

    dt = dt.plusMillis(offset);
    Timestamp ts = new Timestamp(dt.getMillis());

也许这不是得到它的实际方法,但它解决了我的问题。我希望它能帮助任何困在这里的人。

我用这种方法解决了这个问题

String dateUTC = rs.getString("date"); //UTC
DateTime date;
DateTimeFormatter dateTimeFormatter = DateTimeFormat.forPattern("yyyy-MM-dd HH:mm:ss.SSS").withZoneUTC();
date = dateTimeFormatter.parseDateTime(dateUTC);

通过这种方式,您可以忽略强制选择时区的服务器时区。

什么是RS?结果集?您应该在代码中提到这些内容。所以您想修改时间戳,值为:“2013-04-13 22:56:27.0”以包含UTC+03:00偏移量?我怀疑是否可以这样做-您可以使用这里提到的SELECT CONVERT_TZ(..)。我认为这就是如何做到的——将UTC时间转换为指定时区,即东非时间。然后使用它作为参数来选择CONVERT_TZ(..)@davidblaine为什么我需要数据库中的时区列?实际上,我正在从用户的浏览器中检查用户的时区,并试图更改服务器上的时间字符串,而不是数据库上的时间字符串。您应该知道,您得到的
偏移量
没有考虑到所讨论日期的夏令时(DST),因为您要求的是“当前”偏移量,即
新日期时间()
。您应该询问那天的偏移量。@Cebence如果我没有理解错,您就在标记这一点,谢谢:不,我是指您回答中设置
偏移量的第一行代码。您正在使用“now”作为
getOffset()
的参数,因为
newdatetime()
将为您提供当前日期和时间。您正在将该偏移量应用到一个完全不同的日期,该日期可能有相同的偏移量,也可能没有相同的偏移量。@Cebence抱歉,我不知道当前日期时间,因为我只获取用户所在时区的当前时间偏移量。这个偏移量是10800000(3小时)。Mysql有自己的时区(+00:00),我所做的只是在唤醒每个用户的时区时显示他们的真实时间。你是说要注意夏令时,但乔达不是在寻找夏令时吗?
//This Works just fine
DateTime dt = new DateTime();
Log.d("ts",String.valueOf(dt.now()));               
dt=dt.plusYears(3);
dt=dt.minusDays(7);
Log.d("JODA DateTime",String.valueOf(dt));
Timestamp ts= new Timestamp(dt.getMillis());
Log.d("Coverted to java.sql.Timestamp",String.valueOf(ts));
String dateUTC = rs.getString("date"); //UTC
DateTime date;
DateTimeFormatter dateTimeFormatter = DateTimeFormat.forPattern("yyyy-MM-dd HH:mm:ss.SSS").withZoneUTC();
date = dateTimeFormatter.parseDateTime(dateUTC);
//This Works just fine
DateTime dt = new DateTime();
Log.d("ts",String.valueOf(dt.now()));               
dt=dt.plusYears(3);
dt=dt.minusDays(7);
Log.d("JODA DateTime",String.valueOf(dt));
Timestamp ts= new Timestamp(dt.getMillis());
Log.d("Coverted to java.sql.Timestamp",String.valueOf(ts));