Является ли Java TimeZone потокобезопасным?

Я хотел, чтобы мое приложение просто имело один объект TimeZone, который будет использоваться многими объектами SimpleDateFormat и Calendar из других мест одновременно. Это делается для того, чтобы избежать необходимости всегда делать TimeZone.getTimeZone(ID).

Я знаю, что классы SimpleDateFormat и Calendar не являются потокобезопасными, поэтому я настраиваю один поток, чтобы всегда создавать новые экземпляры. Но как насчет 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();
...

Спасибо!

Ответы

Ответ 1

Это не так.

И вам это не нужно. Вы используете его как:

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

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

У вас есть два потока, использующих один и тот же часовой пояс, но поскольку вы не изменяете его, вам не нужно быть потокобезопасным.

Единственное, что вы можете изменить, это ID, но даже тогда вы в порядке, поскольку остальные атрибуты доступны только для чтения

Единственный способ, с помощью которого вы можете столкнуться, - это изменить идентификатор и кешировать себя часовым поясом, если вы всегда получаете его из TimeZone.getTimeZone(), вы тоже в безопасности, потому что этот метод - это поток сейф.

Ответ 2

Я посмотрел один раз на исходный код и пришел к выводу, что это не так.

Посмотрите класс JodaTime часовой пояс. В javadoc говорится, что он потокобезопасен и неизменен.

Ответ 3

Нет явной документации, в которой указано, что TimeZone является потокобезопасным, поэтому самый безопасный маршрут предполагает, что он не является потокобезопасным.

Класс TimeZone имеет два экземпляра-мутатора, относящихся к ID и его смещению по GMT. Здравый смысл скажет, что Calendar.getInstance и SimpleDateFormat не имеют бизнес, изменяющий состояние объекта TimeZone (в первом случае он используется как ключевой ключ, а во втором - как формат форматирования).

Здравый смысл или определенность - ваш выбор.

Ответ 4

Вы не изменяете свой TimeZone, поэтому ваш код должен быть потокобезопасным независимо от того, является ли базовая реализация TimeZone потокобезопасной (за исключением статических методов, например (getTimeZone/getDefault/setDefault).

Ответ 5

Кажется, что все в порядке. Если вы полагаетесь на TimeZone.getDefault(), это будет другая история. Поскольку другой поток потенциально может быть вызван TimeZone.setDefault().