[英]how to locally synchronize two maps?
例如,
class Test{
static Map a = new ...
static Map b = new ...
public void process(){
...
a.put(...);
b.put(...);
}
}
我必須像這樣鎖定:
synchronized(a){
a.put();
}
synchronized(b){
b.put(b);
}
這似乎很尷尬。 還有其他正確的方法嗎? 謝謝。
不,您需要在一個synchronized
塊中執行兩個操作,否則另一個線程可能會看到兩個映射之間的不一致。
一種可能的選擇是使用synchronized
方法,或者您可以使用其他一些私有對象或其中一個映射作為監視器。 這是synchronized方法示例:
static Map a = new ...
static Map b = new ...
public synchronized void process(){
...
a.put(...);
b.put(...);
}
}
你可以使用像這樣的專用對象
Object mapLock = new Object();
同步。
或者您也可以同步a
牢記,即使你需要訪問b
,你需要在同步a
。
this
同步通常不是一個好主意。 我的意思是這是一個壞習慣,這樣做可能最終導致性能不佳或不明顯的死鎖,如果不是這樣,而是你做的其他應用程序。
您還可以考慮使用並發包中的ReadWriteLock。
您需要在一個synchronized
塊中運行這兩個操作。 值得注意的是,在您的示例中,您已經靜態定義了映射,而process()
方法是一個實例方法。 同步該方法將意味着對該實例的調用將被同步,但是對2個不同實例的調用將不會(因為將synchronized關鍵字應用於方法時使用的鎖實際上是this
)。 您可以將process()方法synchronized(Test.class) {}
靜態,也可以使用synchronized(Test.class) {}
塊來確保沒有賽車發生。
您還需要注意如何將地圖公開給客戶端 - 如果您將它們作為屬性提供,那么我可能會將它們用Collections.unmodifiableMap()包裝起來以確保其他任何東西都不能用於它們。你不是在尋找 - 但是這並不能完全防止客戶有一個“奇怪”的時間,因為他們仍會看到變化以可能不安全的方式發生。 因此,我也可能將類型聲明為ConcurrentHashMap以使事情更安全一些(盡管仍然存在一些危險的操作,例如在線程之間共享Iterator)
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.