【发布时间】:2015-11-09 04:47:45
【问题描述】:
我正在尝试验证一个字符串的校验和,在这种情况下,它是通过对每个单独的字符执行 XOR 来计算的。
给定我的测试字符串:
check_against = "GPGLL,5300.97914,N,00259.98174,E,125926,A"
我想它会很简单:
result = 0
for char in check_against:
result = result ^ ord(char)
我知道结果应该是28,但是我的代码给出了40。
我不确定文本应该采用什么编码,尽管我已经尝试在 utf-8 和 ascii 中进行编码/解码,但结果相同。
我在 C 中通过简单地对 char 数组进行 XOR 实现了相同的算法,得到了完美的结果,那么我错过了什么?
编辑
所以不久前,我在 C 中实现(我认为的)相同的东西。我知道它是在一个 Objective-C 项目中,但我认为我只是这样做了。完全错误,首先有一个步骤,我将末尾的校验和字符串值转换为十六进制,如下所示(我在这里填写了一些东西,所以我只粘贴相关的内容):
unsigned int checksum = 0;
NSScanner *scanner = [NSScanner scannerWithString:@"26"];
[scanner scanHexInt:&checksum];
然后我做了以下计算校验和:
NSString sumString = @"GPGLL,5300.97914,N,00259.98174,E,125926,A";
unsigned int sum = 0;
for (int i=0;i<sumString.length;i++) {
sum = sum ^ [sumString characterAtIndex:i];
}
那我就这样比较:
return sum == checksum;
【问题讨论】:
-
另一种检查原始值的方法
map(ord, check_against),然后使用operator.xor减少它,就像reduce(xor, map(ord, check_against))。在 python 3 中,它将是functools.reduce。 -
我相信对于您给定的示例字符串
utf-8与ascii是死路一条,因为 ASCII 字符在 Unicode 中具有相同的值。bytearray(check_against, encoding='utf-8') == bytearray(check_against)在 Python 2 中返回True。 -
另外,最后,你的 C 代码是什么?我确信答案是base10 中的
40和base16 中的0x28。您是如何使用 C 生成输出28的? -
我刚刚将您的 Python 代码直接移植到 C 并验证结果是正确的
40。链接:ideone.com/YK8FOp -
最后一点,似乎没有人承认这一点:
printf("%x\n", 40);导致28被打印出来。