我有一个在线程之间共享的静态int数组:
static int[] res = new int[10];
在一个函数中,我想隔离res中的内容,并且基本上将其值重置为0。以下代码是线程安全的吗?
final int[] copy = res;
res = new int[10];
// do sth with `copy`
如果没有,那么不破坏性能(而不是使用AtomicInteger或Semaphore)是一种更聪明的方法。
答案 0 :(得分:2)
这不是线程安全的。无法保证其他线程何时会看到对静态变量res
的更改。
您可以将其更改为:
static volatile int[] res = new int[10];
然后将保证其他线程下次使用res
变量来提取它。
在这种特殊情况下,您仅重置为零,并且不依赖于先前的res
值,这可能就足够了。
如果您确实依赖先前的值(或其他共享变量),则需要在线程之间实现进一步的同步。
但是,一个警告:其他线程可能仍在操纵“ copy
”变量中的值,因为它们可能已经检索了引用并保留了该引用。
答案 1 :(得分:1)
没有某种形式的同步是不安全的。
一个线程是否可以执行示例中所示的引用交换,而另一个线程正在更新数组?如果是这样,那么该代码非常是不安全的,因为不同的线程可能在res
所引用的数组上存在分歧,因此更新可能会丢失。
即使唯一更新数组的线程与进行交换的线程相同,代码 still 也不安全,因为其他线程可能会看到对数组成员的更新乱序彼此之间,并且对于res
的重新分配而言,是混乱的。
您应该保护对锁res
的所有访问(来自 any 线程)和带锁的数组成员。