目前我有一個數據庫是不是由我管理,我不能做任何更改,id字段是一個smallint 2無符號,它可以給你多達65535 id條目。獲取未使用的下一個ID?
我的問題是,由於上述限制,我需要重新使用ID,我如何才能獲得下一個可用ID或者如何管理具有上述限制的插入?
目前我有一個數據庫是不是由我管理,我不能做任何更改,id字段是一個smallint 2無符號,它可以給你多達65535 id條目。獲取未使用的下一個ID?
我的問題是,由於上述限制,我需要重新使用ID,我如何才能獲得下一個可用ID或者如何管理具有上述限制的插入?
檢查1
是免費的。如果不是:
SELECT MIN(a.id) + 1 AS smallestAvailableId
FROM your_table AS a
LEFT JOIN your_table AS a2
ON a2.id = a.id + 1
WHERE a2.id IS NULL
無論採用哪種方法都可能會因爲競爭條件而導致問題,除非您知道在任何時刻只有一個客戶端訪問數據庫。
要回答你的問題,你認爲什麼是「可用」的ID?請說明一下。直到所有的id已被使用一個簡單的
SELECT MAX(id) + 1 FROM table;
應該做的。如果建立「可用」的ID,例如一個標準,重用那些被標記舊的所有ID,那麼你可以這樣做:
SELECT MIN(id) FROM table WHERE is_old = 1;
然後,只需取消標記選定的ID。
從標籤我推斷出你需要在Java中的id。
我個人會避免加入表格本身。由於您最多有64K行,因此我會將select id from table
轉換爲Java並在Java中搜索id。搜索差距的一種方法是首先對數組進行排序(使用SQL或Java);找到差距就變得微不足道了。
如果您重複執行此操作,則可以緩存該數組並避免每次需要某個ID時都必須運行SQL語句。
無論你做什麼,如果有多個客戶端寫入數據庫,你必須準備好處理競爭條件,其中多個客戶端會嘗試使用相同的ID。您的代碼需要使用鎖定或能夠正常恢復以重新嘗試帶有不同ID的失敗插入(我假設在id
列中存在唯一性約束)。
+1注意競爭條件 – 2010-12-15 18:30:20
真的很優雅。 – Konerak 2010-12-15 17:35:26
如果數據庫爲空IFNULL(MIN(a.id)+ 1,1) – Prix 2010-12-15 18:26:02
假設1如果不空閒則數據庫不爲空... – 2010-12-16 00:15:55