为什么要用“&1”检查负数

问题描述 投票:0回答:1

当我尝试重构 LeetCode 问题的代码时,刚刚遇到了这个问题。问题是比较一个正整数是否小于另一个整数的绝对值。这是我的做法:(我知道有一个 abs() 函数,但更喜欢 NOT 使用它)

if(A < B || A+B < 0)
// do something

其中A是不超过1000的正整数,B可以是任意32位整数。但是,我看到其他比我的解决方案更快的解决方案,如下所示:

if(A<B || (A+B &1))
// do something

我提交了第二个解决方案,其中“ONLY”更改是条件语句。我很惊讶地看到了一点进步。我无法向自己解释为什么第二个条件有效以及为什么它更快。 谁能稍微解释一下吗?

更新

感谢您的快速回复。但是不,这与评论中粘贴的 AND 按位操作问题不同。我一开始就是这么想的。 “&1”应该只是检查整数是奇数还是偶数。我也明白使用 AND 运算的传统方法是比较有效位,这是通过以下方式完成的:

if((A+B >> 31) &1)

这里是问题的链接:
目标总和

c++ bit-manipulation
1个回答
1
投票

考虑值

A == 10

B == -12
,那么 if 子句中的第一个测试自然会失败,但第二个测试也
(尽管它应该不会),因为 A + B 计算为 -2所有位的位表示
但最不重要
设置一个位(提供二进制补码)。 因此,在考虑性能之前,您应该首先考虑代码的

正确性

如果现在考虑性能,实际上只有当底层硬件需要不同数量的 CPU 周期来计算 AND 运算和比较时才可能存在差异 - 我对典型的现代硬件持怀疑态度......即使有

差异(那么很可能比较需要更多周期),编译器可能会自行决定将 < 0 优化为

& 0x80000000
(提供了 32 位整数),从而为两个变体产生完全相同的机器代码(假设您修复了错误)在第二个变体中!)。

如果您确实发现了最小的性能差异,则可能有很多完全不相关的原因欺骗了您,例如测试系统由于传入的网络流量而变得更加活跃,另一个用户开始另一个任务,......对运行其中一项或另一项测试时。如果您想获得绝对可靠的结果,您需要在密封系统(例如专用微控制器)上进行测试(并且结果仍然可以是特定于硬件和编译器的,如上所述!)。

© www.soinside.com 2019 - 2024. All rights reserved.