2012-10-09 30 views
0

我不太明白爲什麼Object.GetHashCode()爲兩個相同的字節數組返回不同的值,但爲不是IEnumerable值類型對象返回相同的值。例如:如何使用C#中的Object.GetHashCode()比較兩個巨大的byte []數組?

byte e = 123; 
Console.WriteLine(e.GetHashCode()); 

byte f = 123; 
Console.WriteLine(f.GetHashCode()); 

輸出

123 
123 

但當

byte[] a = new byte[3] { 1, 2, 3 }; 
Console.WriteLine(a.GetHashCode()); 

byte[] b = new byte[3] { 1, 2, 3 }; 
Console.WriteLine(b.GetHashCode()); 

輸出

46104728 
12289376 

爲什麼會這樣,我怎麼能快速比較兩個巨大數組沒有比較他們的每個元素?

+1

的hashCode平等**!= **平等 – spender

回答

4

GetHashCode沒有爲數組類型定義的 - 你要實現自己的哈希算法。

您看到的值實際上是基於底層引用,因此兩個相同的數組總是具有不同的哈希碼,除非它們是相同的引用。

對於32位或更少的整數類型,哈希碼等於轉換爲32位整數的值。對於64位整數類型Int64,高32位與散列碼的低32位異或(這裏也有一個移位)。

因此,當試圖比較兩個陣列'快速',你必須自己做。

你可先用邏輯檢查 - 長度是相等的,就用相同的字節值等端然後,你必須選擇 - 要麼讀字節 - 通過 - 字節和比較值(或可以讀取4首或8個字節並且使用BitConverter將字節塊轉換爲Int32Int64以製作一對值,可能會更快地檢查相等性)或使用通用散列函數來獲得對等式的良好猜測。

爲此,您可以使用MD5哈希碼 - 使用MD5輸出哈希碼的速度非常快:How do I generate a hashcode from a byte array in C#?

從這樣一個散列函數獲取兩個相同的散列值不會保證保證相等,但是一般情況下,如果您要在同一數據'空間'內比較字節數組,您不應該發生衝突。我的意思是說,總的來說,相同類型的不同數據的例子幾乎總是會產生不同的散列。網絡上有很多比我有資格解釋的更多。

0

默認情況下,引用類型GetHashCode正在計算來自引用而不是來自對象內容的哈希碼。

我覺得你的運氣了,來計算陣列的哈希碼,你需要去通過陣列的內容的,至少一次

1

 
Try by use SHA1CryptoServiceProvider.ComputeHash method? 
It takes a byte array and returns a SHA1 hash which is identical 
for byte arrays. Performance is good.

string byte1hash; string byte2hash;
using (SHA1CryptoServiceProvider sha1 = new SHA1CryptoServiceProvider()) { byte1hash= Convert.ToBase64String(sha1.ComputeHash(byteArray1)); byte2hash= Convert.ToBase64String(sha1.ComputeHash(byteArray2));
} if (string.Equals(byte1hash, byte2hash)) { //States the byte arrays are same.. }

If you are not worried about security, then you go for MD5