2015-11-19 67 views
-6

我期待創建一個簡單的C++散列函數,它將基於字符串輸入返回一個最大範圍內的數字。所以,相同的字符串將始終返回相同的整數值。下面是一個任意的例子,其中最大期望的範圍是36散列函數,可以返回一個基於字符串的整數範圍

Fred Smith -> 25 
tree -> 34 
Frog -> 0 
Fred Smith -> 25 
fred smith -> 7 

這些數字是任意的,但該函數應使用一個算法,確實對字符串和結果的數值計算在限定的範圍內的整數。我最終會重寫這個函數以供在Python 2.7中使用。

我使用vs2008(aka C++ 9)和std :: hash不可用。

我需要一些關於該方法的建議。

+0

像FNV這樣的標準哈希有什麼問題? –

+0

只需'hash(somestring)%hash_upper_bound'? – Paul

+0

剛剛發現std :: hash在vs2008中並不是很容易獲得 – panofish

回答

1
#Very simple minded hash 
def hashval(str, siz): 
    hash = 0 
    # Take ordinal number of char in str, and just add 
    for x in str: hash += (ord(x)) 
    return(hash % siz) # Depending on the range, do a modulo operation. 

print(hashval('stack', 33)) 
+0

由於我使用vs2008,哈希不可用。對於我的用例,我喜歡這種簡單的方法。謝謝 – panofish

2

爲什麼不是std::hash

#include <iostream> 
#include <functional> 
#include <string> 

int main() 
{ 
    int max = 100; 

    std::string str = "Fred Smith"; 
    std::hash<std::string> hash_fn; 

    int num = (int) hash_fn(str) % max; 

    std::cout << num << '\n'; 
} 

輸出:

33

如果你需要一個定製的散列算法的實現,將跨語言工作,我建議首先herehere

0

創建良好哈希的兩個重要元素是哈希表大小和哈希值(添加您自己的不可預知的接觸)。通常會有給定字符串的操作來散列,可能會添加每個字符的ASCII值或類似於某些操作中涉及的字符串的長度。這些是非常簡單的用於字符串的散列示例。

假設我們現在使用的是使用每個字符的ASCII值的字符串中的算法,我們可以將我上面提到的兩個元素,創造我們的哈希函數是這樣的...

int hash(string s, int tableSize) 
{ 
    int sum = 0; 
    for (int i = 0; i < s.length(); i++) 
     sum += int(s[i]) * 3 //<- * 3 being my salt to the hash 

    return sum % tableSize; 
} 

使用黃金數字何時做表大小模數和醃製是很好的做法,因爲它會降低在你的哈希中創建模式的風險。

我希望這能幫助你走上正軌!

+0

雖然[multiplicative hashing](https://en.wikipedia.org/wiki/Universal_hashing#Hashing_strings)不被認爲特別好,但這是非常糟糕的 - 在函數實現以及對其進行編碼:假定將不小於(機器字中可表示的值的數量)/(可能的關鍵元素值的數量)的奇數應用於當前關鍵元素之前的散列值。 [salt](https://en.wikipedia.org/wiki/Salt_%28cryptography%29)用於保護字典攻擊的散列值,這通常不被視爲散列函數的一部分。 – greybeard

+0

有效點greybeard。但是,在我的使用中,散列僅用於基於字符串在0-360之間生成不同的顏色值。 – panofish

0

java中的hashmap使用對象的散列函數來獲取32字節的散列函數和散列映射實現的第二個散列函數,以進一步減少散列的長度。這個問題在這個問題的解析中有解釋:What hashing function does Java use to implement Hashtable class?

您可以看看HashMap實現使用的散列函數,因爲它可以生成所需長度的散列。

您可以將字符串的每個字符的整數表示形式並計算最大模數。 max + 1是你希望散列值最高的值。

編輯:

這個HASH很容易逆轉,所以它取決於您的要求。