2012-11-16 34 views
2

我的網站使用各種資源,從一個單一的域,例如:簡單的散列函數可變長度URL映射到數字(0 ... 3)

http://static.example.com/javascript/common.js 
http://static.example.com/javascript/common.css 
http://static.example.com/javascript/menu/menu.js 
http://static.example.com/javascript/menu/menu.css 
http://static.example.com/images/1804/logo/02000100.jpg 
http://static.example.com/images/1804/headers/main/09400060.png 
http://static.example.com/images/1804/headers/home/1101/06900200-01.jpg 
http://static.example.com/images/1804/headers/home/1101/06900200-02.jpg 

我需要一個非常簡單的字符串哈希函數映射這些網址爲數字,數字爲0,1,2和3.該算法應該是確定性和統一的。我已經標記了PHP的問題,但通用的答案是可以接受的。

你可能猜到了爲什麼我需要這個;我打算改變網址,例如:

http://0.static.example.com/javascript/common.js 
http://2.static.example.com/javascript/common.css 
+0

我要說'的strlen($ STR)%$ num' ......這絕對快:) :) –

+0

是快但不統一...看到包含單詞_headers_的網址?我將在一個頁面上使用它們中的大約15個,因此20個URL中的15個將具有散列= 3。 –

+0

是的,無疑地,它更適用於更像人類的圖像名稱:) –

回答

2

我寧願做一個crc32散列的字符串,並取其模極限。

代碼:

function numeric_hash($str, $range) { 
    return sprintf("%u", crc32($str)) % $range; 
} 

用法:

$str = "http://static.example.com/javascript/common.js 
http://static.example.com/javascript/common.css 
http://static.example.com/javascript/menu/menu.js 
http://static.example.com/javascript/menu/menu.css 
http://static.example.com/images/1804/logo/02000100.jpg 
http://static.example.com/images/1804/headers/main/09400060.png 
http://static.example.com/images/1804/headers/home/1101/06900200-01.jpg 
http://static.example.com/images/1804/headers/home/1101/06900200-02.jpg"; 
$urls = explode("\n", $str); 

foreach($urls as $url) { 
    echo numeric_hash($url, 4) . "\n"; 
} 

輸出:

1 
3 
3 
3 
1 
3 
1 
3 
+0

+1爲簡單起見:) –

+0

什麼是'hexdec'?我用你的示例代碼得到負數,這種方式不是問題。 –

+0

@SalmanA,哎呀,我以爲'crc32'返回一個十六進制值。你必須使用32位php,函數可以根據[manual](http://php.net/manual/en/function.crc32.php)返回負整數。我確定把它包裝在'abs()'中也會給你一個正常的分佈。 – Dogbert

1

如果你有大量的網址,你應該只是一個強大的散列,然後採取mod <noBuckets>

MD5(URL) % 4 

如果你有幾個URL,或者你有不平大小或通話頻率的「隨機」分佈可能會很糟糕,您應該創建四個列表並靜態地將您的URL分配給每個列表,無論是手動還是使用基於每個URL的請求數的啓發式。