假設有一個人試圖從銀行賬戶A轉賬20美元到銀行賬戶B,另一個人試圖同時從銀行賬戶B轉賬30美元到銀行賬戶A.爲什麼這應該導致僵局?
它不會。這不是真正的銀行業務的工作原理。
你大概是從某種類比或簡化的版本推理來演示這個概念。
線程1獲取的鎖從A版本A的鎖獲取B的鎖撤櫃$ 18添加$ 20到B版本B的鎖
像這樣的事情很可能確實是真實的代碼來完成。
需要注意的是,如果由於某種原因我們無法獲得鎖B,我們需要再次獲得鎖A才能返回20美元,因爲如果我們在失敗的情況下無法返回20美元,我們不會沒有一筆交易要麼完全成功,要麼完全失敗,20美元可能會消失。因此,如果在未能獲得鎖B之後,我們可能無法再獲得鎖A,這是不可接受的。如果某種東西可能會獲得A和B的鎖,並根據它們所保護的值作出決定,這也是不可接受的;他們的總和在這一點上是不正確的。
另一種可能的方法是訂購鎖。如果A總是出現在B之前,那麼無論它們以何種方式轉移資金,兩個線程總是會試圖在鎖B之前獲得鎖A,並且永遠不會發生死鎖。一個重要的警告是,如果你有鎖B並意識到你也需要鎖A,那麼你必須在獲得鎖A之前釋放鎖B.
另一種可能的方法是在死鎖時一個事務丟失,其工作撤消並且其鎖釋放也許在重試之前,或者可能有例外(或者在例外之前可能有一定次數的重試)。這在數據庫鎖定中很常見。請注意,這需要一些控制代碼來注意已完成的工作,以便它可以撤消。交易事務數據庫就是這樣,但絕大多數多線程程序都是如此。