Java的TimeZone是线程安全的吗?

时间:2009-11-12 23:38:04

标签: java timezone thread-safety

我希望我的应用程序只有一个TimeZone对象,它将同时被其他地方的许多SimpleDateFormatCalendar个对象使用。这是为了避免总是TimeZone.getTimeZone(ID)

我知道SimpleDateFormatCalendar类不是线程安全的,这就是为什么我配置一个线程来始终创建它们的新实例。但是TimeZone呢?我不清楚我是否可以安全地做到以下几点:

final TimeZone tz = TimeZone.getTimeZone("GMT");
...
//Thread 1.
Thread t1 = new Thread(Runnable(){
    public void run()
    {
        Calendar cal = Calendar.getInstance(tz);
        ...
        SimpleDateFormat sdf = new SimpleDateFormat();
        sdf.setTimeZone(tz);
        ...
    }
});
t1.start();
...
//Thread 2.
Thread t2 = new Thread(Runnable(){
    public void run()
    {
        Calendar cal = Calendar.getInstance(tz);
        ...
        SimpleDateFormat sdf = new SimpleDateFormat();
        sdf.setTimeZone(tz);
        ...
    }
});
t2.start();
...

谢谢!

5 个答案:

答案 0 :(得分:7)

我看了一下它的源代码并得出结论它不是。

查看JodaTime timezone课程。它在javadoc中说它是线程安全且不可变的。

答案 1 :(得分:6)

不是。

你不需要它。您的代码将其用作:

final TimeZone tz = TimeZone.getTimeZone("GMT");
 ......
// thread 1 SimpleDateFormat instance
sdf.setTimeZone(tz);

// thread 2 SimpleDateFormat instance
sdf.setTimeZone(tz);

你有两个线程使用相同的时区,但由于你没有修改它,你不需要它是线程安全的。

你可以修改的唯一内容是ID,但即便如此,你也可以,因为其他属性是只读的

唯一可以解决问题的方法是更改​​ID并自行缓存时区,如果你总是从TimeZone.getTimeZone()获得它也是安全的,因为该方法 线程安全。

答案 2 :(得分:2)

没有明确的文档表明TimeZone是线程安全的,所以最安全的路由是假设它不是线程安全的。

TimeZone类有两个实例变更器,与ID及其GMT偏移有关。常识会说Calendar.getInstance和SimpleDateFormat没有业务修改TimeZone对象状态(在第一种情况下,它被用作查找键,在第二种情况下,用作格式化上下文)。

常识或确定性 - 您的选择。

答案 3 :(得分:1)

您没有修改TimeZone,因此无论TimeZone的底层实现是否是线程安全的(除了静态方法,如(getTimeZone / getDefault / setDefault)),您的代码应该是线程安全的。

答案 4 :(得分:0)

出现即可。如果你依赖于TimeZone.getDefault()那将是一个不同的故事。由于另一个线程可能正在调用TimeZone.setDefault()。