线程安全?如何实现?
- 如果你的代码所在的进程中有多个线程在同时运行,而这些线程可能会同时运行这段代码。如果每次运行结果和单线程运行的结果是一样的,而且其他的变量的值也和预期的是一样的,就是线程安全的。
- 线程安全问题都是由全局变量及静态变量引起的。
- 若每个线程中对全局变量、静态变量只有读操作,而无写操作,一般来说,这个全局变量是线程安全的; 若有多个线程同时执行写操作,一般都需要考虑线程同步,否则的话就可能影响线程安全。
对于线程不安全的对象我们可以通过如下方法来实现线程安全:
- 加锁 利用
Synchronized
或者ReenTrantLock
来对不安全对象进行加锁,来实现线程执行的串行化,从而保证多线程同时操作对象的安全性,一个是语法层面的互斥锁,一个是 API 层面的互斥锁。 - 非阻塞同步来实现线程安全。原理就是: 通俗点讲,就是先进行操作,如果没有其他线程争用共享数据,那操作就成功了; 如果共享数据有争用,产生冲突,那就再采取其他措施(最常见的措施就是不断地重试,直到成功为止)。这种方法需要硬件的支持, 因为我们需要操作和冲突检测这两个步骤具备原子性。通常这种指令包括
CAS SC
,FAI TAS
等。 - 线程本地化,一种无同步的方案,就是利用
Threadlocal
来为每一个线程创造一个共享变量的副本来(副本之间是无关的)避免几个线程同时操作一个对象时发生线程安全问题。