0

可能重复:
java中的枚举如何线程安全?

让有一个enum

public enum Type
{
    ONE, TWO, THREE, FOUR
}

在循环Type.values()中访问数组线程是否安全,例如在静态方法中?for例如:

public static void process()
{
    for (Type type:Type.values())
    {
        // Do something
    }
}

此外,如果使用这些值的任何子集定义一个静态数组变量,那么读取是否是线程安全的?例如:

public static final Type[] TYPES = new Type[] {TWO, THREE};

public static void process()
{
    for (Type type:TYPES)
    {
        // Do something
    }
}

在这两种情况下,process()方法可能属于与Type enum数组types的定义不同的类。

此外,该TYPES数组可以在 中定义一次,Type enum并由 that 的静态方法返回enum

那么,鉴于上述情况,如果多个线程同时运行该process()方法,代码是否是线程安全的(至少对于读取TYPES数组的值而言)?

4

3 回答 3

3

该方法Type.values()每次都返回一个新数组。这样做是因为数组是可变的,并且每次都必须返回一个新副本以保证线程安全。

于 2012-07-09T18:44:59.027 回答
1

enum 保证线程安全,它们是不可变的。所以,线程不能修改枚举的状态。

第二种情况,当你定义final为时,它也是线程安全的,你不能修改错误的引用。

请记住,您不能只更改“引用”,但可以更改数组的状态。

于 2012-07-09T18:44:40.430 回答
1

其他人已经指出该values()方法每次都返回一个新数组,因此它是线程安全的。

但是,要回答您的第二个问题:

如果使用这些值的任何子集定义一个静态数组变量,那将是线程安全的吗?

不 ,任何 public static数组都不安全,因为数组元素总是可变的。也就是说,任何线程都可以更改TYPES[0]为任何其他线程Type,这在存在多个线程的情况下是不安全的——甚至在单线程程序中也是如此。

更好的是公开 a List<Type>,然后可以安全地使其不可变(例如,使用Collections.unmodifiableList())。

于 2012-07-09T18:47:59.387 回答