Java 中的鎖是多線程編程中最常用的技術(shù)之一,主要用于解決線程安全問題。但是,從鎖的實(shí)現(xiàn)方式上可以分為悲觀鎖和樂觀鎖。
悲觀鎖是一種保守的鎖機(jī)制,假設(shè)資源在多線程環(huán)境下總是會被其他線程爭用。因此,當(dāng)一個(gè)線程需要對資源進(jìn)行操作時(shí),它首先會將資源加鎖,確保其他線程無法訪問該資源并修改數(shù)據(jù)。在 Java 中,悲觀鎖的實(shí)現(xiàn)方式主要是 synchronized 關(guān)鍵字和 ReentrantLock 類。
public synchronized void update(int newValue) { int val = getValue(); someExpensiveOperation(); setValue(newValue); }
樂觀鎖是一種更為積極的鎖機(jī)制。它假設(shè)資源在多線程環(huán)境下不會發(fā)生沖突,并不直接對資源加鎖,而是在對資源進(jìn)行操作時(shí),檢查是否有其他線程對資源進(jìn)行了修改。如果沒有,那么當(dāng)前線程可以成功地對資源進(jìn)行修改;否則,需要進(jìn)行重試或者放棄操作。在 Java 中,樂觀鎖的實(shí)現(xiàn)方式主要是使用版本號控制機(jī)制和CAS(Compare and Swap)算法等。
public class OptimisticUpdate { private int value; public void update(int newValue) { int currentVersion = getVersion(); while (!compareAndSwap(currentVersion, newValue)) { currentVersion = getVersion(); } } // Getter and setter methods omitted }
在面試中如果被問到鎖的問題,一定要了解悲觀鎖和樂觀鎖的特點(diǎn)和使用場景,對于 ReentrantLock 的一些高級知識點(diǎn)也需要了解,并且在代碼編寫中避免出現(xiàn)死鎖等問題。