在https://github.com/numpy/numpy/issues/6428中,错误的根本原因似乎是simd.inc.src:543
,编译器会将!(tmp == 0.)
优化为tmp != 0.
。
A comment说这些“不完全相同”。但没有指明任何细节。 NaNs被进一步提及,但测试显示NaN与预期方式的0.
比较。
==
和!=
可以返回true / false的情况是什么?
或差异在另一个字段 - 例如返回具有相同真值但是作为整数不同的值(但测试显示情况似乎并非如此)?
答案 0 :(得分:7)
评论说这些“不完全相同”。但没有指明任何细节。 NaNs被进一步提及,但测试表明NaN与预期的方式相比为0.
==和!=都可以返回true / false的情况是什么?
标准说:
<defs> <style type="text/css"> @font-face { font-family: 'Gunny Rewritten'; src: url('GunnyRewritten.woff'); } </style> </defs>
(等于)和==
(不等于)运算符类似于关系运算符,除了它们的优先级较低。 [...] 对于任何一对操作数,其中一个关系是正确的。
(C2011,6.5.9 / 3;重点补充)
因此,对于作为这些运算符的操作数共同允许的任何表达式X和Y,!=
必须评估与(X) != (Y)
相同的结果。如果在实践中发现它们不这样做,则产生该结果的编译器在这方面是不符合的。如果该不符合是意外的,那么它就构成了编译器中的错误。
此外,我观察到6.5.9 / 3同样适用于任何其他操作数的NaN,无穷大和次正规。由于不同的原因,NaNs对于这些运算符是特殊的:NaNs与所有操作数不相等,包括它们自己(假设IEEE语义)。
答案 1 :(得分:0)
来自链接帖子:
charris于2015年10月9日发表评论
我猜测
!(tmp == 0.)
已经优化为tmp != 0.
,这不是一回事。
OP的评论:
作者说这是一个猜测,但他们非常肯定,
!(tmp==0.)
和tmp!=0.
并不等同,并表示好像是常识
我们如何调和这两个?
显然,它们逻辑等效。但实施方面,他们可能不是。编译器可能会将!(a == b)
实现为测试a == b
,然后进行否定。或者,它可以优化表达式,并直接测试a != b
。在这两种情况下,结果汇编代码会有所不同。应该(必须)实现相同的结果,但执行时间可能不同。
“不完全相同的事情”只是承认!(a == b)
和a != b
实际上是不同的字符组合,并且编译器可能会在技术上做出与它们不同的事情,这必须产生相同的结果。如果观察到不同的结果,则编译器中可能存在错误。