我一直在研究python和Java的MD5实现,遇到了一个困扰我的怪癖。在
下面的python脚本说明了这个问题:
# -*- coding: utf-8 -*-
import hashlib
def md5hash(x):
m = hashlib.md5()
m.update(x)
return m.hexdigest()
print md5hash('\xdb')
print md5hash('Û')
输出:
^{pr2}$我希望这两个摘要是等价的,因为Û
应该与{
import java.security.MessageDigest;
import java.security.NoSuchAlgorithmException;
public class Test {
public static void main(String[] args) throws Exception {
MessageDigest m = MessageDigest.getInstance("MD5");
m.update("\u00db".getBytes());
System.out.println(bytesToHex(m.digest()));
m.update("Û".getBytes());
System.out.println(bytesToHex(m.digest()));
}
final protected static char[] hexArray = "0123456789abcdef".toCharArray();
public static String bytesToHex(byte[] bytes) {
char[] hexChars = new char[bytes.length * 2];
for ( int j = 0; j < bytes.length; j++ ) {
int v = bytes[j] & 0xFF;
hexChars[j * 2] = hexArray[v >>> 4];
hexChars[j * 2 + 1] = hexArray[v & 0x0F];
}
return new String(hexChars);
}
}
输出:
31ecfb09f120720a55d96a2034f5d00b
31ecfb09f120720a55d96a2034f5d00b
Java的输出与预期一致。这使我相信md5hash('\xdb')
输出的结果不正确,但我不确定我遗漏了什么。有什么想法吗?在
你的假设是不正确的。Python源代码的开头是:
在这种情况下,
^{pr2}$Û
不是等价于\xdb
;而是两个字节:Python在这里是完全一致的:
在Java中,您开始使用Unicode代码点,将其转换为UTF-8字节:
Python等价物将使用}转义序列:
unicode
字符串文本和\uhhhh
或{注意
u
前缀以生成unicode
字符串。\xdb
没有u
前缀是一个字节串,而不是Unicode码位,只有当你将它解码为拉丁语1时,才会得到相同的Unicode字符串:您可能想学习Python和Unicode;请参见:
Python Unicode HOWTO
Pragmatic Unicode作者:Ned Batchelder
为了完整起见:
Û是UTF-8中的
C3 9B
,您似乎正在使用它(这是您声明的编码)。DB
将是ISO-8859-1。在塔达!在
相关问题 更多 >
编程相关推荐