code

2016年12月1日 星期四

Java concurrency 1 - Thread safe是什麼意思?

Thread-safe class

可以定義成:如果一個class instance在多個threads存取他的過程中,所有可能的執行緒的存取順序都能產出spec定義的行為,而且存取他的threads並不用做任何synchronization之類的工程,那這個class就可以說是thread safe。


Stateless object永遠是thread-safe的

下面這個class只有一個method,而且沒有任何data member,換句話說,不論是class instance或是method裡面都沒有state的存在,這讓access這個class instance的thread彷彿在access不同的instance,所以是一個thread safe class:



Non Atomic operation is not thread-safe

如果把上面的class加入一個state來計算request數目,我們可能會這樣做:


++count這行程式實際上不是atomic operation!所謂atomic operation是指單一thread會完整執行完畢產生預期效果後,此operation才會換其他thread執行

++count實際上是三個CPU指令:(1)讀取couont (2)計算新的count值 = count+1 (3)寫入新的count值,這是所謂的read-modify-write operation

兩個thread如果執行這個method,可能會產生以下的非預期狀況:



Race condition

一個多執行緒程式,如果必須要依賴時間點的巧合才能產生預期結果的話,那代表可能有race condition。一種常見的race condition pattern是check-then-act的設計:透過觀察某一個事件的發生,去決定要進行的動作。問題出在多執行緒的程式執行中,這個觀察到的事件,可能在要進行動作的時候就不成立了,主要是因為觀察和動作並非atomic。

一個常見的check-then-act設計是singleton pattern :


singleton pattern通常利用lazy initialization的技巧來達成單一instance的目的,但是由於getInstance()並沒有impelemnt成atomic operation,所以會產生race condition。


利用現有Thread-safe object來達成thread-safety

上面的UnsafeCountingFactorizer class,我們可以利用java提供的AtomicLong來取代long,進而保證thread-safety。

這是一個快速的解決方案,能如此達成的話,盡量先採取這個approach。



沒有留言:

張貼留言