PHP如何產生唯一的數字ID,注意是數位,不要字串的
回複內容:
PHP如何產生唯一的數字ID,注意是數位,不要字串的
樓主,你這個問題大了。
twitter,weibo等都是專門做了一個發號器來解決這個問題的。
twitter那一套東西,叫做snowflake,樓上已經有人指出過了。這玩意一共64bit,前41bit是以微妙的時間戳記,10bit是機器護著說伺服器id,最後12bit是seq序列累加計數器。
weibo的方法和twitter是很類似的,將id分割為n個段,每段採集一定的資料來源,最後產生一個高度唯一的id。
flickr是用的一個叫做ticketserver的玩意,使用純mysql來實現的。
create table ticket(
id bigint unsigned not null auto_increment primary key,
stag char(1) not null default '',
unique key stag
(stag
)
)engine=myisam;
先插入一條記錄,然後再用replace去擷取這個id。
replace into ticket(stag) values('a');
select last_insert_id();====>ID
然後是,UUID也是一個不錯的選擇,但是UUID產生的序列太長,而且mysql本身不具備原生支援(我假裝樓主用的mysql),但樓主可以嘗試把uuid當作binary(16)來儲存效果會好些兒。但樓主說是純數字,那就白搭了。
還有一種,是我群裡聽到的。就是提前產生一大坨可用的唯一的id,用的時候直接取然後del掉,這也是可行的,因為說這個方案的那個人是個大神。為什麼提前產生呢,我覺得最主要一條就是預防高並發情況下,兩個人得到的id是一樣 ; 提前產生的話可以排隊一個一個產生,確保唯一。當然,他們的建置原則是什麼我就不太清楚了。樓主可以參考twitter的做法。
另有,mongodb內建的objectId也是一種高度唯一的序列,樓主可以利用Mongodb產生的直接拿過來用,但也要確保高並發情況下,兩個人或者更多人得到同一個id,雖然機率很低。但樓主說是純數字,那還是白搭。
如果樓主玩的單機,那就不用太糾結唯一id的問題,主鍵自增就可以做唯一id。太長遠的問題,現在可以考慮,但不能過於拘泥。如果樓主是分布式,那就是要必須了要這個東西了。
base_convert(uniqid(), 16, 10);
可以
redis incr
推薦一個 我自己在用的唯一數字ID產生器
https://github.com/sschiau/Particle.php
Particle
Language: PHP
64bits int Time Based ID Generator
PHP implementation of Twitter Snowflake ID Generator
Uncoordinated
For high availability within and across data centers, machines generating ids should not have to coordinate with each other.
Solution
System Clock Dependency
You should use NTP to keep your system clock accurate.
How to use it
Generate Particle ID
Change const EPOCH in particle class to today epoch time w/ miliseconds (13 digits)
$machineID = 1; // Machine ID (aka Server ID no) Particle::generateParticle($machineID);
Time from Particle ID (w/ milisecond precision)
$particleID = '4611692470816737853'; Particle::timeFromParticle($particleID);
樓主應該說明唯一ID用途和使用情境,資料庫自增ID,還有PHP是弱類型的,數字和字串數實值型別是可以通用,相互轉換的.
沒辦法的, 除非你記錄產生過的數字, 否則即使隨機函數,時間戳記產生數字都會出現重複的。
twitter全域唯一ID產生服務:snowflake(https://github.com/twitter/snowflake)
引用:
http://www.oschina.net/p/snowflake
http://www.cppblog.com/tx7do/archive/2014/06/10/207248.html
uniqid is really good, why don't you use it ? just need convert to number , first answer is cool.
sorry I can't type Chinese, because it's disabled on chrome , I think it's a bug of segmentfault.com
應該先說明情境,單機唯一還是多久唯一,單次請求唯一還是多次請求唯一
時間戳記加隨機數位組合,但是保險起見,最好產生之後還是需要到記錄過的ID池驗證一下
@magicgod i think you can @SegmentFault to solve your question
不太明白題主的意思,是用在什麼情境呢?在資料庫的話直接設定ID自增不就可以了嗎?如果是數組的話,那就直接$i++咯
可以用時間戳記
可以產生一個保證同一時空內不重複的uuid或者guid,這個開源的類有很多,自己也可以寫,根據目前時間戳+隨機因子.隨機因子可包括當前的pc的mac地址和隨機字串和當前代碼的行數等等,PHP內建的函數:
com_create_guid可以完成你的功能.如果你不滿足,github上有許多開源的實現.
補充:1應該是要固定長度 2遇到字母轉成數字或將隨機引起用數字表示
有一個辦法,用目前時間戳,純數字
貼上我一段虛擬碼,我使用過的id產生器
$id = substr(strtotime(date("Y-m-d", time())), 0, 2) . substr(strrev(microtime()), 0, 2) . substr(mt_rand(), 0, 5) . substr(rand(), 0, 2);$sql = "SELECT id FROM table WHERE id=" . $id . " LIMIT 1";$data mysql_query($sql);
思路大概是時間戳記加上隨機數拼湊,具體實現當然樓主根據需求再做修改
雖然根據計算基本可以得出唯一,但是不能確保,最好入庫加唯一鍵,通過查詢來保證唯一值
事先產生一個數字池,然後要用的時候從池子取出就行了
如果那個數字釋放了,直接放回池子就可以了
這樣的話,隨機啥的都好解決