SimpleDateFormat 没有正确解析日期
SimpleDateFormat not parsing date correctly
我很困惑为什么 SimpleDateFormat
没有正确解析以下输入数据。
我试图在 String
上测试各种可能允许的日期格式,看看它是否可以使用其中一种格式正确解析。
注意:我使用的其他不正确的日期格式报告解析错误。这就是我希望看到的。
我做错了什么?或者,我可以做些什么作为解决方法?
String dformat = "MM-dd-yyyy";
String cDate = "2013-12-28";
SimpleDateFormat f = new SimpleDateFormat(dformat);
Date dd = f.parse(cDate);
结果是成功了。解析的日期是:
Date Fri Sep 12 00:00:00 PST 195
嗯,日期应该是2013 年12 月28 日。
在这种情况下,我希望看到(就像我看到的其他无效格式一样):
java.text.ParseException: Unparseable date: "2013-12-28"
你的代码应该是这样的:
String dformat = "yyyy-MM-dd";
String cDate = "2013-12-28";
SimpleDateFormat f = new SimpleDateFormat(dformat);
Date dd = f.parse(cDate);
你的问题日期格式有误。
嗯,dformat 不符合 cDate 格式。因此,您必须在 dformat 中提供 cDate,或者您必须在 ""yyyy-MM-dd"
中更改 dformat
您的格式模式和日期字符串不多。
更改为:
String dformat = "yyyy-MM-dd";
您真的应该考虑使用 java.util.Date 的新 java 8 版本,它是 java.time.LocalDate 和 java.time.LocalDateTime 作为 SDK 的一部分。由于您遇到问题的原因,这些日期 API 被认为更稳定。这是一个例子。
String armisticeDate = "2013-12-28";
LocalDate aLD = LocalDate.parse(armisticeDate);
System.out.println("Date: " + aLD);
String armisticeDateTime = "2013-12-28T11:50";
LocalDateTime aLDT = LocalDateTime.parse(armisticeDateTime);
System.out.println("Date/Time: " + aLDT);
如果您想创建不同的格式,可以执行以下操作。
String anotherDate = "04 Apr 2016";
DateTimeFormatter df = DateTimeFormatter.ofPattern("dd MMM yyyy");
LocalDate random = LocalDate.parse(anotherDate, df);
System.out.println(anotherDate + " parses as " + random);
有关完整文档,请查看 Oracle 页面。
https://docs.oracle.com/javase/8/docs/api/java/time/format/DateTimeFormatter.html
获取错误信息:
java.text.ParseException: Unparseable date: "2013-12-28"
您需要致电:
f.setLenient(false);
正如 parse(String source, ParsePosition pos)
的 javadoc 所说:
By default, parsing is lenient: If the input is not in the form used by this object's format method but can still be parsed as a date, then the parse succeeds. Clients may insist on strict adherence to the format by calling setLenient(false)
.
嗯,SimpleDateFormat
被认为是 problematic and bugged class, with 。
可能发生的事情与问题 described in this article 类似。考虑您的模式和输入:
MM-dd-yyyy
2013-12-28
它可能将月读为“20”,日读为“3”,年读为“-28”? (或其他一些值,因为我不确定它如何将 2-28
解释为 4 位数字)。这场混乱的最终结果是一个完全错误的、奇怪的日期——不要问我它是如何得出最终结果的,这对我来说是一个谜。
无论如何,当模式与输入格式不匹配时可能会发生这种情况,并且 SimpleDateFormat
读取的实际值将不是那么可预测的并且有点 counter-intuitive。但真正重要的是这个 class 有很多问题和设计缺陷,默认情况下它很宽松,所以它试图成为 "smart" 并在给出错误之前做很多奇怪的事情。
如果您想验证输入,只需关闭宽松模式,按照 Andreas 的建议调用 f.setLenient(false)
。当输入与模式不匹配时,这将引发异常。
但是如果您使用的是 Java 8,那么您应该使用 java.time API,它的性能要好得多,它解决了 SimpleDateFormat
存在的许多问题。
要检查字符串是否包含特定格式的日期,请使用 java.time.format.DateTimeFormatter
。这个 class 默认情况下不像 SimpleDateFormat
那样宽松,所以它应该按预期工作:
// use the format "month-day-year"
DateTimeFormatter fmt = DateTimeFormatter.ofPattern("MM-dd-yyyy");
// try to parse a string in a different format (year-month-day)
LocalDate dt = LocalDate.parse("2013-12-28", fmt); // exception
上面的代码试图创建一个 LocalDate
,一个代表日期(只有日、月和年)的 class。但是如果你只想验证输入(而不将其分配给任何变量),你可以只使用格式化程序:
fmt.parse("2013-12-28"); // exception
我很困惑为什么 SimpleDateFormat
没有正确解析以下输入数据。
我试图在 String
上测试各种可能允许的日期格式,看看它是否可以使用其中一种格式正确解析。
注意:我使用的其他不正确的日期格式报告解析错误。这就是我希望看到的。
我做错了什么?或者,我可以做些什么作为解决方法?
String dformat = "MM-dd-yyyy";
String cDate = "2013-12-28";
SimpleDateFormat f = new SimpleDateFormat(dformat);
Date dd = f.parse(cDate);
结果是成功了。解析的日期是:
Date Fri Sep 12 00:00:00 PST 195
嗯,日期应该是2013 年12 月28 日。 在这种情况下,我希望看到(就像我看到的其他无效格式一样):
java.text.ParseException: Unparseable date: "2013-12-28"
你的代码应该是这样的:
String dformat = "yyyy-MM-dd";
String cDate = "2013-12-28";
SimpleDateFormat f = new SimpleDateFormat(dformat);
Date dd = f.parse(cDate);
你的问题日期格式有误。
嗯,dformat 不符合 cDate 格式。因此,您必须在 dformat 中提供 cDate,或者您必须在 ""yyyy-MM-dd"
中更改 dformat您的格式模式和日期字符串不多。 更改为:
String dformat = "yyyy-MM-dd";
您真的应该考虑使用 java.util.Date 的新 java 8 版本,它是 java.time.LocalDate 和 java.time.LocalDateTime 作为 SDK 的一部分。由于您遇到问题的原因,这些日期 API 被认为更稳定。这是一个例子。
String armisticeDate = "2013-12-28";
LocalDate aLD = LocalDate.parse(armisticeDate);
System.out.println("Date: " + aLD);
String armisticeDateTime = "2013-12-28T11:50";
LocalDateTime aLDT = LocalDateTime.parse(armisticeDateTime);
System.out.println("Date/Time: " + aLDT);
如果您想创建不同的格式,可以执行以下操作。
String anotherDate = "04 Apr 2016";
DateTimeFormatter df = DateTimeFormatter.ofPattern("dd MMM yyyy");
LocalDate random = LocalDate.parse(anotherDate, df);
System.out.println(anotherDate + " parses as " + random);
有关完整文档,请查看 Oracle 页面。
https://docs.oracle.com/javase/8/docs/api/java/time/format/DateTimeFormatter.html
获取错误信息:
java.text.ParseException: Unparseable date: "2013-12-28"
您需要致电:
f.setLenient(false);
正如 parse(String source, ParsePosition pos)
的 javadoc 所说:
By default, parsing is lenient: If the input is not in the form used by this object's format method but can still be parsed as a date, then the parse succeeds. Clients may insist on strict adherence to the format by calling
setLenient(false)
.
嗯,SimpleDateFormat
被认为是 problematic and bugged class, with
可能发生的事情与问题 described in this article 类似。考虑您的模式和输入:
MM-dd-yyyy
2013-12-28
它可能将月读为“20”,日读为“3”,年读为“-28”? (或其他一些值,因为我不确定它如何将 2-28
解释为 4 位数字)。这场混乱的最终结果是一个完全错误的、奇怪的日期——不要问我它是如何得出最终结果的,这对我来说是一个谜。
无论如何,当模式与输入格式不匹配时可能会发生这种情况,并且 SimpleDateFormat
读取的实际值将不是那么可预测的并且有点 counter-intuitive。但真正重要的是这个 class 有很多问题和设计缺陷,默认情况下它很宽松,所以它试图成为 "smart" 并在给出错误之前做很多奇怪的事情。
如果您想验证输入,只需关闭宽松模式,按照 Andreas 的建议调用 f.setLenient(false)
。当输入与模式不匹配时,这将引发异常。
但是如果您使用的是 Java 8,那么您应该使用 java.time API,它的性能要好得多,它解决了 SimpleDateFormat
存在的许多问题。
要检查字符串是否包含特定格式的日期,请使用 java.time.format.DateTimeFormatter
。这个 class 默认情况下不像 SimpleDateFormat
那样宽松,所以它应该按预期工作:
// use the format "month-day-year"
DateTimeFormatter fmt = DateTimeFormatter.ofPattern("MM-dd-yyyy");
// try to parse a string in a different format (year-month-day)
LocalDate dt = LocalDate.parse("2013-12-28", fmt); // exception
上面的代码试图创建一个 LocalDate
,一个代表日期(只有日、月和年)的 class。但是如果你只想验证输入(而不将其分配给任何变量),你可以只使用格式化程序:
fmt.parse("2013-12-28"); // exception