防止日期转换溢出
Posted
技术标签:
【中文标题】防止日期转换溢出【英文标题】:Preventing overflow on date conversion 【发布时间】:2017-10-10 19:22:52 【问题描述】:在使用日期输入时,我们创建了一个我们认为非常错误的值:2017 年 2 月 45 日或“2017-02-45”。 这导致将溢出的天数添加到下个月,我们以 3 月的日期结束。 有没有办法廉价地检查这些日期不一致? 当前计划是将字符串转换为日期到文本并与原始值进行比较。 接下来是创建一个 Java UDF 并使用它来检查和测试格式。
【问题讨论】:
adding the overflow of days into the next month
是什么意思?将 2017-02-45 转换为日期将返回 null。
发布您的代码。通常使用至少三个日期时间框架,每个框架在这方面都有不同的行为。并解释与 Apace Hive 的联系(如此标记)。
我们看到的是 2017-02-45 变成了 ~2017 年 3 月 17 日的日期值。它不是空值。一些研究表明它类似于 DataFormat.setLenient(false)。
@user1281598 如果您的意思是java.text.DateFormat
,那么该类是麻烦的旧日期时间类的一部分,这些类现在是遗留的,被 java.time 类所取代。避免使用Date
、Calendar
、DateFormat
类。
setLenient(false)
在旧的 DateFormat 中。
【参考方案1】:
tl;博士
使用现代 java.time 类。
使用ResolverStyle.STRICT
或SMART
解析通过LocalDate
时抛出的DateTimeParseException
。
详情
取决于您使用的日期时间类。
现代 java.time 类使用称为resolver style 的三种模式中的任何一种进行解析:
ResolverStyle.STRICT(默认) ResolverStyle.SMART ResolverStyle.LENIENT解析“2017-02-45”时,默认的STRICT
会抛出java.time.format.DateTimeParseException
。
LocalDate.parse( "2017-02-45" )
java.time.format.DateTimeParseException:无法解析文本“2017-02-45”:DayOfMonth 的值无效(有效值 1 - 28/31):45
SMART
同上,抛出异常。
只有LENIENT
接受错误输入并进行调整。
输入:2017-02-45
输出:2017-03-17
参见this live code example in IdeOne.com,我们在其中尝试了三种模式。
String input = "2017-02-45" ;
System.out.println( "input: " + input ) ;
for( ResolverStyle rs : ResolverStyle.values() )
try
System.out.println( "---------------" ) ;
System.out.println( "Parsing with ResolverStyle: " + rs ) ;
DateTimeFormatter f = DateTimeFormatter.ISO_LOCAL_DATE.withResolverStyle( rs ) ;
LocalDate ld = LocalDate.parse( input , f ) ;
System.out.println( "ld.toString(): " + ld ) ;
catch ( DateTimeParseException e )
System.out.println( "Caught exception for ResolverStyle: " + rs ) ;
input: 2017-02-45
---------------
Parsing with ResolverStyle: STRICT
Caught exception for ResolverStyle: STRICT
---------------
Parsing with ResolverStyle: SMART
Caught exception for ResolverStyle: SMART
---------------
Parsing with ResolverStyle: LENIENT
ld.toString(): 2017-03-17
【讨论】:
以上是关于防止日期转换溢出的主要内容,如果未能解决你的问题,请参考以下文章
如何防止 pandas 将原始数据库日期格式转换为 pandas 日期格式