Java 分析字符串date to date

Java 分析字符串date to date,java,parsing,date,date-formatting,Java,Parsing,Date,Date Formatting,我有一个格式为“YYYY-MM-dd HH::MM:ss”的日期字符串。每次解析字符串时,我都会得到错误的日期。(“Sun Dec 29 10:10:10 CET 2013”)。代码如下: DateFormat timeFormat = new SimpleDateFormat("YYYY-MM-dd HH:mm:ss"); Date startDate = timeFormat.parse("2014-08-10 10:10:10"); System.out.println(startDate

我有一个格式为“YYYY-MM-dd HH::MM:ss”的日期字符串。每次解析字符串时,我都会得到错误的日期。(“Sun Dec 29 10:10:10 CET 2013”)。代码如下:

DateFormat timeFormat = new SimpleDateFormat("YYYY-MM-dd HH:mm:ss");
Date startDate = timeFormat.parse("2014-08-10 10:10:10");
System.out.println(startDate);

返回“Sun Dec 29 10:10:10 CET 2013”。如何正确解析日期字符串?

您使用了错误的格式。您需要
yyyy
而不是
yyy

如果你看一看,你会发现

y   Year
Y   Week year
其中“”与循环同步

现在,为什么
YYYY
2014年
返回2013年

要回答这个问题,你需要了解日历是如何决定一周属于某一年的。规则很简单:

  • 如果本周的最后
    N
    天(通常N=4,但由所用日历中的
    getminimadaysinfirstweek
    确定)属于XXXX年,则本周属于XXXX年
  • 周从
    getFirstDayOfWeek
    产生的日期开始。这个结果取决于区域设置,但在下一个示例中,我们将使用星期一作为一周的第一天
示例1。

假设一周的第一天是星期一,一周属于某一年所需的天数是4,让我们尝试确定XXXX年1月的第一周,如下所示:

       January XXXX
Mon Tue Wed Thu Fri Sat Sun 
 27  28  29  30  31   1   2
  3   4   5   6   7   8   9
...
从第一行开始的一周只包含两天,这两天属于XXXX年(到1月),第一天和第二天

 27  28  29  30  31   1   2
                    ^^^ ^^^  //days which belong to January
但这比下周属于XXXX年所需的天数少

  3   4   5   6   7   8   9
包含属于XXXX年的7天。由于第一行中的周不属于XXXX年,因此第二周中的第一周将从XXXX年1月3日开始。这意味着,如果我们用格式
YYYY
解析值
XXXX
,我们将得到
1月3日XXXX

示例2。

现在让我们假设XXXX年的日历如下所示

       January XXXX
Mon Tue Wed Thu Fri Sat Sun 
 30  31   1   2   3   4   5
  6   7   8   9  10  11  12
...
正如你在本周所看到的

 30  31   1   2   3   4   5
其最后5天属于XXXX年,超过了所需的4天
->这意味着本周属于XXXX年,
->这也是XXXX年的第一周
->这意味着今年的第一周从12月30日(XXXX-1)开始 ->这最后意味着,如果您使用
yyy
格式解析该年份,您将得到值XXXX-1


示例2实际上是2014年的情况,这就是为什么年份被解释为2013年的原因

顺便说一句,如果您决定使用周-年格式来设置月和日,您还需要使用特殊格式来描述

  • 您希望设置一年中的哪一周
  • 星期几
因此,您必须使用

w   Week in year
u   Day number of week (1 = Monday, ..., 7 = Sunday)
(小时、分钟、秒是时间的一部分,而不是日期,因此
H
m
s
可以采用这种格式)

比如说

DateFormat format = new SimpleDateFormat("YYYY-ww-uu HH:mm:ss");
Date date = format.parse("2004-53-7 10:10:10");
System.out.println(date);

它将被解析为
Sun Jan 02 10:10:10 CET 2005

而不是使用
YYYY
您需要使用
YYYY

Y
表示周/年,而
Y
表示年。周年基于一年中第一个完整的周开始的时间(这取决于设置),因此与一年中的周略有不同(有时很大)

请参阅javadoc:

评论多于回答?@hd1这是解决方案(所以答案,质量低,但仍然是答案),我正在研究“为什么”部分。@hd1这解决了问题。如果它解决了问题,接受答案并忽略我的评论。“为什么”是
YYYY
是,这与年份、FYI、麻烦的旧日期时间类不同,例如,和
java.text.SimpleTextFormat
现在被类取代。看见