提问人:MrArsGravis 提问时间:3/10/2022 更新时间:3/10/2022 访问量:98
是否可以比较两个多字整数,每个字只有一个比较?
Is it possible to compare two multi-word integers with only one comparison per word?
问:
这个问题与语言无关,但我会使用 C,因为这是我编码它的内容。
给定两个整数,每个整数跨越单词,比较这些多单词数字的最有效方法是什么,例如确定?(†)a
b
n_word
a < b
作为一个具体的例子,我们可以考虑 和 是长度为 8 位的整数数组,每个数组代表 1 位整数(并假设 big-endian 排序)。(††)或者,可以使用常规的旧十进制数来表达问题,例如,第一个数字 (4) 在哪里等。a
b
n_word
8*n_word
a = 456
a[0]
我有以下有效的代码,但我想知道是否有可能摆脱两种比较之一:
for (unsigned int i = 0; i < n_word; ++i) {
if (a[i] > b[i]) {
i = n_word + 1; /* use as magic number to indicate that a > b */
break;
}
else if (a[i] < b[i]) {
break;
}
}
然后结果由 after 循环的值决定:i
if i < n_word, then a < b
if i > n_word, then a > b
if i == n_word, then a == b
但我实际上并不想/需要区分所有三种情况;将两个箱子合二为一是完全可以的。但是,如果我只是删除,例如,在不更改任何其他内容的情况下进行比较,那么(在十进制示例中)和 (其中 ) 的计算结果将与 和 (where ) 相同,这显然是不正确的。替换为 in the loop 似乎同样是虚假的。>
a = 200
b = 123
a > b
a = 100
b = 123
a < b
<
<=
† 虽然,或者他们的任何一个相反也是可以接受的。a > b
†† 不,当然,我实际上并不是要比较两个 32 位整数,而更像是 10 个 32 位整数,它们形成一个非常长的整数,超出了任何原生类型的能力范围。
答:
0赞
Vlad Feinstein
3/10/2022
#1
看来你的担忧(有不止一个比较)是没有根据的。
该指令设置 FLAG 寄存器,并且两个条件跳转都基于这些标志执行。ASM
CMP
评论
memcmp
uint32_t a[10] = {1}, b[10] = {2};
printf("%d\n", memcmp(a, b, sizeof a));
memcmp
memcmp
uint32_t
memcmp
memcmp
uint8_t