使用方法调用引用参考分配中的线程安全问题

时间:2014-05-22 17:43:24

标签: java multithreading thread-safety

我有以下代码:

class SomeClass {
    private Map<String, String> someMap = null;

    public String getValue(String key) {
        if (someMap == null) {
            someMap = initialize(); // initialize() is some method which returns a proper map.
        }
        return someMap.get(key);
    }
}

假设我不关心someMap多次初始化,是否还有其他线程安全问题需要我关注。

根据what-operations-in-java-are-considered-atomic,参考分配肯定是atmoic。 someMap的赋值是否在方法调用initialize()后保证发生(对我而言似乎合乎逻辑)。线程是否有可能看到部分构造的someMap。如果不是地图,我有其他类型的对象。

2 个答案:

答案 0 :(得分:4)

代码是线程安全的。如果两个线程在同一个对象上调用方法getValue,则有可能一个线程看到部分创建的someMap

为了避免此问题,您必须删除数据争用。最简单的解决方案是将someMap声明为volatile。要记住的简单规则是:如果代码不包含数据竞争,那么所有执行都将显示为顺序一致。

答案 1 :(得分:0)

即使你输入volatile也不是线程安全,因为如果两个线程同时被调用getValue方法,可能会发生以下情况

1)主题1&amp;线程2 检查 if(someMap == null),两者都会通过并尝试重新初始化。

2)两者都将重新初始化参考。线程1返回旧引用,哪一个被线程2覆盖。

3)因此,请参阅链接Double Checked Locking in Singleton