2011-07-11 73 views
2

有什麼辦法可以讓我的模型ID(主鍵)生成隨機唯一的8位數字,只包含數字而不是默認的自動增量? 一位客戶請求了這個特定的8位數字的功能,所以我不能多說理由。自定義唯一ID

我想使用PHP uniqid,但它是13位數字,也包含字母。

有什麼想法?

謝謝。

更新

我忘了告訴我需要的ID隨機生成的被保存每一個新的紀錄。

只是想問一下生成ID的機制,然後保存ID(也是屬性)。我是否必須首先檢查隨機生成的ID是否存在另一個相同的密鑰,然後保存屬性或什麼?

+1

身份證必須是隨機的,還是隻有8位? –

+0

這個ID必須是隨機的 –

回答

1

是的,你可以。當談論AI時,我假設你在MySQL上。只是不要將它設置爲自動增量,併爲其他列插入值。您可以創建一個函數或方法,它將隨機或按特定順序(算法)最多佔用8個數字。

​​。

考慮INT(11)值可能接受從-2147483648到2147483647.這將適合你8位數的數字。如果在稍後客戶端請求更大的數字,您可能需要切換到BIGINT。

我用它來設置主鍵爲無符號,它允許你一個0到4294967295

之間的配合數爲PHP函數 - 8位數字生成器:

<?php 

mt_srand(); 
$id = mt_rand(10000000, 99999999); 

?> 

你可以閱讀更多關於在PHP文檔上的mt_srand()和mt_rand()。據說他們比srand()和rand()更好。

+0

讓它隨機生成一個ID是一個壞主意,我們可以有多個具有相同ID的行,這會造成很大的問題。這就是爲什麼我建議填充實際ID,以便它有13位數字。 – dotty

+0

@dotty:這就是爲什麼你使用數據庫'UNIQUE'約束。 – phant0m

+0

是的,這是樣本,您的方法也適用,作爲第三個。另一個檢查是必要的。 是的,這也是事實,主鍵也是唯一的。 – Rolice

1

保留ID,但填充它。

$id = 6; 
$padded_id = sprintf("%013d", $id); 
// This will print 0000000000006 

那將墊$id,以便它的13位長。

每當您需要顯示ID時,請使用一個函數將其轉換,如下所示。

function padId($id){ 
    return sprintf("%013d", $id); 
} 

或者你可以讓你的表稱爲pad-id一排,然後運行該功能,當你創建一個記錄(與mysql_insert_id沿(獲取ID剛剛插入))。

+0

這個工作,但他想得到8位數字。 –

+0

NINJA EDIT。你說的8位數字,我的例子打印13! – dotty

+0

在原始的問題,我的意思是:) –

3

爲什麼不保留自動增量,而是將其設置爲從主鍵而不是1開始10000000?

ALTER TABLE some_table AUTO_INCREMENT=10000000

1

最好的方法取決於你的客戶的隨機性需求的一個細微環節 - 當他們說隨機做他們的意思是完全不可預測的,或只是很難預測?在Lewinski的審判中,我的意思不是聽起來像克林頓,但是當你的客戶說隨機會影響你是否有可能滿足要求。

如果客戶想要隱藏用戶ID(對於某些感知到的安全性好處)並且使它們幾乎不可能預測或反向工程,那麼這非常困難。如果客戶滿意只是「難」預測(我懷疑),那麼你可以做一些簡單的事情,類似於MD5方法(@Dotty)。但md5不是collision resistant。即使使用最好的,可證明的獨特哈希算法(其中md5不是),如果用戶數量大於用戶ID允許的數字位數(8),則會出現衝突問題。你有大約27位可以使用8位十進制數字。這意味着你可能在2^N/2 = 2 ^(27/2)之後發生衝突,這大約是10K用戶。所以如果你的客戶的用戶列表接近10K用戶,那麼即使是最好的散列算法也會花費大量的時間過濾掉所有的衝突。 要解決這個問題,不使用過濾器和非確定性算法,只需使用簡單的「Full Cycle」算法。有些會產生僞隨機數(PRN),這些僞隨機數保證是唯一的,並保證完全覆蓋你想要覆蓋的範圍(例如,所有8位正整數的集合)。如果您需要對用戶註冊序列進行逆向工程,只需重新運行全循環PRN發生器,無論您使用什麼初始值。如果您的客戶想要讓黑客更容易地對您的用戶ID序列進行逆向工程,那麼您可以保留這個初始值,像私人密鑰一樣。

您的客戶端的另一個問題是在用戶標識中是否允許前導零。如果是這樣(並且客戶的隨機性要求是自由的),那麼維基百科上的簡單的Full Cycle算法將很適合你。它可以蒸餾成2行PHP。 無論使用哪種算法,最好在單獨的表中生成正式的8位半隨機用戶ID列表,然後只要從表頂部「彈出」該值(刪除該行)就可以了你添加一個新用戶。數據庫內存的要求不應該過高,並且會簡化用戶體驗,消除由複雜的,非確定性的隨機數生成器和唯一性過濾器引起的任何延遲和內存吞噬。試圖在線創建用戶ID,實際上,可以想象,您可以通過一些哈希算法無限期地阻止用戶註冊,從而進入永久循環。這種失速(由於永久碰撞)可能不會發生,直到用戶1000或10000.相比之下,使用脫機查找表方法,您可以輕鬆地添加其他客戶端指定的過濾器,如消除具有前導零的ID;如果客戶從不想看到ID爲1的用戶(00000001)。而且你會事先知道是否所有東西都能正常工作,沒有任何掛起。