天天看点

java时间 format方法_Java时间处理类SimpleDateFormat的parse和format方法的正确使用

SimpleDateFormat 是一个各种项目中使用频度都很高的类,主要用于时间解析与格式化,频繁使用的主要方法有parse和format.

parse方法:将字符串类型(java.lang.String)解析为日期类型(java.util.Date)

format方法:将日期类型(Date)数据格式化为字符串(String)

因为用的很多,所以在使用的时候需要关注更多细节,才能避免更多的坑。(踩得坑多了,才能成为一个会填坑的程序员。)

1. SimpleDateFormat是线程不安全的

官方文档解释如下(参见SimpleDateFormat):

Synchronization

Date formats are not synchronized. It is recommended to create separate format instances for each thread.

If multiple threads access a format concurrently, it must be synchronized externally.

Date formats 是线程不安全的。推荐为每个线程创建单独的format实例。如果多线程并发访问同一个format实例,必须加同步操作。

错误的实现(前提是DateUtils.parseString()方法被多线程调用)

public class DateUtils {

public static SimpleDateFormat format = new SimpleDateFormat("yyyy-MM-dd HH:mm");

// incorrect while be called by multiple threads

public Date parseString(String datetime) throws Exception {

return format.parse(datetime);

}

}

正确实现:

class DateUtils {

public static SimpleDateFormat format = new SimpleDateFormat("yyyy-MM-dd HH:mm");

private static final Object LOCK = new Object();

// OK

public Date parseString(String datetime) throws Exception {

synchronized (LOCK) {

return format.parse(datetime);

}

}

// OK

public Date parseStringV2(String datetime) throws Exception {

SimpleDateFormat format = new SimpleDateFormat("yyyy-MM-dd HH:mm");

return format.parse(datetime);

}

}

2.SimpleDateFormat解析异常java.text.ParseException: Unparseable date

这个问题在stackoverflow上大概出现了1000+,在很多时候程序使用SimpleDateFormat都能正常执行,并不会报错;但有时发现日志出现

java.text.ParseException: Unparseable date: "2017-03-20 02:10"异常,为什么还抛出这种异常呢?

先来看看代码:

public Date parseStringV2(String datetime) throws Exception {

SimpleDateFormat format = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");

return format.parse(datetime);

}

可以看到输入时间为:2017-03-20 02:10, 解析的格式为:yyyy-MM-dd HH:mm:ss.

经过测试发现,当使用format方法将Date转成String时,SimpleDateFormat可实例化为任意期望的时间格式;但是使用parse方法将String转为Date时,SimpleDateFormat定义的格式与参数String的格式必须完全一致,不然就会出现Unparseable date。

另外,当使用Restful api服务时,后端Server与前端APP系统语言(本地环境)存在差异,也有可能出现“输入时间为:2017-03-20 02:10, 解析的格式为:yyyy-MM-dd HH:mm,格式完全一致,parse偶尔也会解析出错”,因为存在偶然不确定行,解决方案还持续分析中。