2009-10-12 29 views
1

我在MySQL 5(InnoDB)中有一個表,用作守護進程處理隊列,因此它經常被訪問非常。通常每天插入約25萬條記錄。當我選擇要處理的記錄時,會使用FOR UPDATE查詢來讀取它們以消除競爭條件(所有內容均基於事務處理)。在MySQL中處理高負載表的常見做法

現在我正在開發一個「隊列檔案」,我偶然發現了一個嚴重的死鎖問題。我需要從表中刪除「已執行」記錄,因爲它們正在處理(實時),但如果我這樣做(每天兩次),表中每隔一段時間就會死鎖。

我雖然正在向延遲刪除(低負載時每天一次),但這並不能消除問題,只會使其不那麼明顯。

在處理MySQL中的高負載表時是否有一種常見的做法?

回答

1

InnoDB鎖定它檢查的所有行,而不僅僅是請求的行。

查看this question瞭解更多詳情。

您需要創建一個與您的搜索條件完全匹配的索引,以擺脫不必要的鎖定並確保使用它。

不幸的是,DML查詢MySQL不接受提示。

+0

嗯,有趣。如果我使用「SELECT id FROM table where foo = bar LIMIT 1 FOR UPDATE」,會怎麼樣呢? - 這樣可以確保只有一行被鎖定? – clops 2009-10-12 12:35:03

+0

否。如果優化器要選擇全表掃描,它將在引擎找到符合標準的第一行之前鎖定所有檢查的行。 – Quassnoi 2009-10-12 12:47:15