我使用以下方法散列字符串3C970E3BF535
:
internal static string Hash(string content)
{
System.Security.Cryptography.KeyedHashAlgorithm ha = System.Security.Cryptography.KeyedHashAlgorithm.Create();
string asmKey = "Some key";
byte[] hashkey = System.Text.Encoding.ASCII.GetBytes(asmKey);
byte[] data1 = System.Text.Encoding.ASCII.GetBytes(content);
byte[] data2 = System.Text.Encoding.ASCII.GetBytes(content.ToLower());
System.Security.Cryptography.HMACSHA512 hmac = new System.Security.Cryptography.HMACSHA512(hashkey);
byte[] hashmac1 = hmac.ComputeHash(data1);
byte[] hashmac2 = hmac.ComputeHash(data2);
string hashmacencoded1 = System.Text.Encoding.ASCII.GetString(hashmac1);
string hashmacencoded2 = System.Text.Encoding.ASCII.GetString(hashmac2);
return string.Format("{0:X}", hashmacencoded1.GetHashCode());
}
我得到的输出是2BED23B1
。长度为8
。
如果我使用此方法反转字符串:
private static string Reverse(string s)
{
char[] charArray = s.ToCharArray();
Array.Reverse(charArray);
return new string(charArray);
}
然后重新哈希它,我得到7个字符 - 707D653
而不是非反向哈希的8个字符,尽管它反转或不反转这一事实根本不重要,因为哈希尽管有输入, 应该返回相同的长度。
我已经切换了我们实际使用的密钥,因此如果您使用上面的代码,则无法重现该问题。如果我们使用密钥,问题就会弹出。发生了什么事?
答案 0 :(得分:1)
您不能使用System.Text.Encoding.ASCII.GetString
来表示哈希,因为哈希只是一个(伪)随机字节分类,而不是ASCII字符串的二进制表示。
相反,您可以将其表示为base64字符串。
Convert.ToBase64String(hashmac1); // ABCDEF123== for example
您也不应该测试结果的GetHashCode()
- 这是在.NET框架内部用于基于键的数据结构的不同代码,例如Dictionary
,{{1只输出变量,而不是变量的哈希码 - 变量是哈希码。
答案 1 :(得分:1)
string.GetHashCode
的结果始终是32位有符号整数。
在这种情况下,您的结果碰巧有一个前导零,当您执行string.Format("{0:X}", ... )
这有各种其他问题(你为什么要得到哈希的哈希码?)但这就是你实际问过的问题的答案。