2014-01-23 37 views
0

我的大部分數據庫都使用IDENTITY列作爲主鍵。我正在數據庫中寫入更改日誌/審計跟蹤,並且想要使用ID BIGINT按順序保留更改的陷阱。SQL Server 2008自定義序列ID

雖然BIGINT非常大,但它會在一天內耗盡數字,而且我的設計在此時無法正常工作。我已經意識到我的其他ID列的這個問題,並打算最終轉換爲GUID/UUID,就像我以前在Postgres中使用過的那樣。

GUID需要16個字節,BIGINT需要8個。對於我當前的任務,我想留在BIGINT中節省空間和排序。在Postgres下,我創建了一個自定義序列,其中前兩位數字爲當年,而固定數量的數字爲年內的序列。年份發生變化時,序列發生器會自動重置序列。

SQL Server 2008沒有序列生成器。我的研究發現了一些想法,其中大部分涉及使用表維護序列號,更新事務內的數據,然後使用它在單獨的事務中分配給我的數據。

我想寫一個SP或函數來更新序列,並在寫入行之前從目標表上的觸發器調用時返回新值。有很多想法,但都似乎都在討論鎖定問題和隔離問題。

有沒有人有關於如何自動執行此ID分配的建議,保護進程不會在併發寫入中分配重複項並防止鎖定延遲問題?

+0

爲什麼不使用自動生成的IDENTITY值?你爲什麼試圖自己創造這些? –

+0

如果你從1開始使用'BIGINT IDENTITY',並且每秒插入**一千行**,那麼在達到922 quadrillion限制之前,你需要令人難以置信的** 2.92億年** ....這是否真的**是你的擔憂? –

回答

0

存儲過程容易出現問題,如阻塞和死鎖。但是,有辦法解決這個問題。

現在,爲什麼不開始在負範圍的底部關閉ID?

CREATE TABLE FOO 
(
ID BIGINT IDENTITY(-9223372036854775808, 1) 
) 

這給你一個範圍-9,223,372,036,854,775,808 9,223,372,036,854,775,807。

你真的要吃掉2^63 + 2^63的數字嗎?

如果你仍然致力於其他解決方案,我可以給你一個工作代碼片。但是,必須使用應用程序鎖和可分離的序列化程序。

依賴於超時設置和服務器負載,它仍然容易出現超時或阻塞。

總之,2012年引入了序列。這基本上是你想要的。