使用xor运算符进行布尔检查是一种好习惯吗?

Pet*_*ter 149 java conditional xor bitwise-operators logical-operators

由于其简洁性,我个人喜欢在布尔检查的上下文中有意义的,或者,^运算符.我更喜欢写作

if (boolean1 ^ boolean2)
{
  //do it
}
Run Code Online (Sandbox Code Playgroud)

if((boolean1 && !boolean2) || (boolean2 && !boolean1))
{
  //do it
}
Run Code Online (Sandbox Code Playgroud)

但是我常常从其他有经验的Java开发人员(不仅仅是新手)那里得到一些困惑,有时会评论它应该如何仅用于按位操作.

我很好奇关于^运营商使用的最佳实践.

小智 296

你可以简单地使用!=.

  • *"有什么问题!="*`bool1 ^ bool2 ^ bool3`对我来说比`bool1!= bool2!= bool3更合乎逻辑 (36认同)
  • @vemv,`!=`为`boolean`s产生正确的结果(但不是'布尔`,所以要小心).它并不总是漂亮,例如`(some!= null)!=(other!= null)`不是很易读.你要么必须在显式布尔值中提取部分,要么在单独的方法中提取`!=`. (27认同)
  • 原因如下:`a ^ b` =>"a或b但不是两者","a!= b` =>"a不等于b".(@RobertGrant所说的).如果他们知道xor是什么的话,大多数人会更容易理解第一个(这对于了解你是否在计算领域非常有用......) (23认同)
  • 我的脑袋疼.那么可以!=产生不正确的结果? (4认同)
  • @ HaroldR.Eason重要的挑剔在这里:`a!= b` =>"a不是对B的识别" (2认同)

Mar*_*tin 27

我想你已经回答了自己的问题 - 如果你从别人那里得到奇怪的外表,那么选择更明确的选项可能会更安全.

如果你需要对它进行评论,那么你最好用更详细的版本替换它,而不是让人们首先提出问题.

  • 我可以断言你,当你认真地写``(boolean1 &&!boolean2)||时,你会得到奇怪的外表.(boolean2 &&!boolean1)`在现实生活中的应用程序代码中...... (6认同)

小智 17

我发现我有很多类似的对话.一方面,您有一种紧凑,有效的方法来实现您的目标.另一方面,你有一些其他团队可能无法理解的东西,使得将来很难维护.

我的一般规则是询问所使用的技术是否是合理的,期望程序员一般都知道.在这种情况下,我认为期望程序员知道如何使用布尔运算符是合理的,因此在if语句中使用xor是可以的.

作为一些不合适的例子,请使用xor交换两个变量而不使用临时变量.这是一个我不希望每个人都熟悉的技巧,所以它不会通过代码审查.


Dre*_*Dre 14

如果您评论它,我认为没关系,例如// ^ == XOR.


Cor*_*oss 10

你总是可以将它包装在一个函数中,以给它一个详细的名称:

public static boolean XOR(boolean A, boolean B) {
    return A ^ B;
}
Run Code Online (Sandbox Code Playgroud)

但是,在我看来,对于那些不知道^运算符对于谷歌来说非常快的人来说并不难.在第一次之后不难记住.由于您要求其他用途,因此通常使用XOR进行位屏蔽.

您还可以使用XOR在两个变量中交换值,而不使用第三个临时变量.

// Swap the values in A and B
A ^= B;
B ^= A;
A ^= B;
Run Code Online (Sandbox Code Playgroud)

这是与XOR交换相关Stackoverflow问题.


Ate*_*ral 6

我最近在工作中的JavaScript项目中使用了xor,最后添加了7行注释来解释发生了什么.在这种情况下使用异或的理由是,术语(之一term1在下面的示例)可以采取不是两个而是三个值:undefined,truefalse而另一个(term2)可以是truefalse.我将不得不为undefined案例添加额外的检查,但是使用xor,以下就足够了,因为xor强制第一个术语首先被评估为布尔值,让我们undefined将其视为false:

if (term1 ^ term2) { ...
Run Code Online (Sandbox Code Playgroud)

最后,它有点矫枉过正,但无论如何我想把它留在那里,就像一个复活节彩蛋.


小智 5

if((boolean1 && !boolean2) || (boolean2 && !boolean1)) 
{ 
  //do it 
} 
Run Code Online (Sandbox Code Playgroud)

恕我直言这个代码可以简化:

if(boolean1 != boolean2) 
{ 
  //do it 
} 
Run Code Online (Sandbox Code Playgroud)


Gun*_*son 5

考虑到代码清晰度,我的观点是在布尔检查中使用XOR不是XOR位运算符的典型用法.根据我的经验,Java中的按位XOR 通常用于实现掩码flag toggle行为:

flags = flags ^ MASK;
Run Code Online (Sandbox Code Playgroud)

Vipan Singla撰写的这篇文章更详细地解释了用例.

如果你需要在你的例子中使用按位XOR,请评论你使用它的原因,因为它甚至可能需要一个有点文化的读者停下来理解你使用它的原因.