多线程环境下使用 DateFormat

个人专题目录


DateFormat 类是一个非线程安全的类。javadocs 文档里面提到"Date formats是不能同步的。 我们建议为每个线程创建独立的日期格式。 如果多个线程同时访问一个日期格式,这需要在外部加上同步代码块。"

如何并发使用DateFormat类

1. 同步

最简单的方法就是在做日期转换之前,为DateFormat对象加锁。这种方法使得一次只能让一个线程访问DateFormat对象,而其他线程只能等待。

private final DateFormat format = new SimpleDateFormat("yyyyMMdd");

public Date convert(String source) throws ParseException {
    synchronized (format) {
        Date d = format.parse(source);
        return d;
    }
}

2.使用ThreadLocal

另外一个方法就是使用ThreadLocal变量去容纳DateFormat对象,也就是说每个线程都有一个属于自己的副本,并无需等待其他线程去释放它。这种方法会比使用同步块更高效。

private static final ThreadLocal df = new ThreadLocal() {
    @Override
    protected DateFormat initialValue() {
        return new SimpleDateFormat("yyyyMMdd");
    }
};

public Date convert(String source) throws ParseException {
    Date d = df.get().parse(source);
    return d;
}

3.Joda-Time

Joda-Time 是一个很棒的开源的 JDK 的日期和日历 API 的替代品,其 DateTimeFormat 是线程安全而且不变的。

private final DateTimeFormatter fmt = DateTimeFormat.forPattern("yyyyMMdd");

public Date convert(String source) {
    DateTime d = fmt.parseDateTime(source);
    return d.toDate();
}

4.Apache commons-lang中的FastDateFormat

private String initDate() {
    Date d = new Date();
    FastDateFormat fdf = FastDateFormat.getInstance("yyyy-MM-dd HH:mm:ss");
    return fdf.format(d);
}

你可能感兴趣的:(多线程环境下使用 DateFormat)