布尔运算符的差异:&与&&和 |与||
我知道 &&
和 ||
的规则,但是 &
和 |
是什么?请用例子向我解释这些。
I know the rules for &&
and ||
but what are &
and |
? Please explain these to me with an example.
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(11)
这些是按位 AND 和按位 OR 运算符。
感谢 Carlos 指出 Java 语言规范中的相应部分 (15.22.1,15.22.2) 关于操作员基于其输入的不同行为。
事实上,当两个输入都是布尔值时,运算符被视为布尔逻辑运算符,其行为类似于条件与 (
&&
) 和条件或 (||
) ) 运算符,除了它们不会短路这一事实,因此,虽然以下情况是安全的:这不是:
“短路”意味着运算符不一定检查所有条件。在上面的示例中,仅当
a
不为null
时,&&
才会检查第二个条件(否则整个语句将返回 false,并且无论如何检查以下条件都是没有意义的),因此a.something
的语句不会引发异常,或者被认为是“安全的”。&
运算符始终检查子句中的每个条件,因此在上面的示例中,当a
实际上是时,可能会计算a.something
null
值,引发异常。Those are the bitwise AND and bitwise OR operators.
Thanks to Carlos for pointing out the appropriate section in the Java Language Spec (15.22.1, 15.22.2) regarding the different behaviors of the operator based on its inputs.
Indeed when both inputs are boolean, the operators are considered the Boolean Logical Operators and behave similar to the Conditional-And (
&&
) and Conditional-Or (||
) operators except for the fact that they don't short-circuit so while the following is safe:This is not:
"Short-circuiting" means the operator does not necessarily examine all conditions. In the above examples,
&&
will examine the second condition only whena
is notnull
(otherwise the whole statement will return false, and it would be moot to examine following conditions anyway), so the statement ofa.something
will not raise an exception, or is considered "safe."The
&
operator always examines every condition in the clause, so in the examples above,a.something
may be evaluated whena
is in fact anull
value, raising an exception.我认为您正在谈论两个运算符的逻辑含义,这里您有一个表格简历:
<短路求值、最小求值或麦卡锡求值(以约翰·麦卡锡命名)是某些编程语言中某些布尔运算符的语义,其中只有第一个参数才执行或求值第二个参数参数不足以确定表达式的值:当 AND 函数的第一个参数计算结果为 false 时,整体值必须为 false;当 OR 函数的第一个参数计算结果为 true 时,整体值也必须为 true。
不安全意味着运算符始终检查子句中的每个条件,因此在上面的示例中,当 x 实际上是 0 值时,可能会计算 1/x,从而引发异常。
I think you're talking about the logical meaning of both operators, here you have a table-resume:
Short-circuit evaluation, minimal evaluation, or McCarthy evaluation (after John McCarthy) is the semantics of some Boolean operators in some programming languages in which the second argument is executed or evaluated only if the first argument does not suffice to determine the value of the expression: when the first argument of the AND function evaluates to false, the overall value must be false; and when the first argument of the OR function evaluates to true, the overall value must be true.
Not Safe means the operator always examines every condition in the clause, so in the examples above, 1/x may be evaluated when the x is, in fact, a 0 value, raising an exception.
我知道这里有很多答案,但它们似乎都有点令人困惑。因此,在对 Java oracle 学习指南进行了一些研究之后,我提出了何时使用 && 的三种不同场景。或&。
这三种情况是逻辑与、按位与和布尔与。
逻辑与:
逻辑 AND(又名条件 AND)使用 && 运算符。它的短路含义是:如果左操作数为 false,则不会评估右操作数。
示例:
在上面的示例中,打印到 x 控制台的值将为 0,因为 if 语句中的第一个操作数为 false,因此 java 不需要计算 (1 == ++x) 因此 x 将不被计算。
按位与:
按位 AND 使用 & 运算符。它用于对值执行按位运算。通过查看二进制数的运算,可以更容易地了解发生了什么,例如:
正如您在示例中看到的,当数字 5 和 12 的二进制表示形式排成一行时,执行按位 AND 只会产生一个二进制数其中两个数字中的相同数字都是 1。因此 0101 & 1100 == 0100。十进制表示为 5 & 1100 == 0100。 12 == 4。
布尔与:
现在,布尔 AND 运算符的行为与按位 AND 和逻辑 AND 类似,但也有不同。我喜欢将其视为在两个布尔值(或位)之间执行按位 AND,因此它使用 & 运算符。布尔值也可以是逻辑表达式的结果。
它返回 true 或 false 值,与逻辑 AND 非常相似,但与逻辑 AND 不同的是,它不是短路的。原因是,为了执行按位 AND,它必须知道左操作数和右操作数的值。这是一个例子:
现在,当运行 if 语句时,即使左操作数为 false,表达式 (1 == ++x) 也会被执行。因此 x 打印出来的值将是 1,因为它是递增的。
这也适用于逻辑 OR (||)、按位 OR (|) 和布尔 OR (|)
希望这能消除一些困惑。
I know there's a lot of answers here, but they all seem a bit confusing. So after doing some research from the Java oracle study guide, I've come up with three different scenarios of when to use && or &.
The three scenarios are logical AND, bitwise AND, and boolean AND.
Logical AND:
Logical AND (aka Conditional AND) uses the && operator. It's short-circuited meaning: if the left operand is false, then the right operand will not be evaluated.
Example:
In the above example the value printed to the console of x will be 0, because the first operand in the if statement is false, hence java has no need to compute (1 == ++x) therefore x will not be computed.
Bitwise AND:
Bitwise AND uses the & operator. It's used to preform a bitwise operation on the value. It's much easier to see what's going on by looking at operation on binary numbers ex:
As you can see in the example, when the binary representations of the numbers 5 and 12 are lined up, then a bitwise AND preformed will only produce a binary number where the same digit in both numbers have a 1. Hence 0101 & 1100 == 0100. Which in decimal is 5 & 12 == 4.
Boolean AND:
Now the boolean AND operator behaves similarly and differently to both the bitwise AND and logical AND. I like to think of it as preforming a bitwise AND between two boolean values (or bits), therefore it uses & operator. The boolean values can be the result of a logical expression too.
It returns either a true or false value, much like the logical AND, but unlike the logical AND it is not short-circuited. The reason being, is that for it to preform that bitwise AND, it must know the value of both left and right operands. Here's an ex:
Now when that if statement is ran, the expression (1 == ++x) will be executed, even though the left operand is false. Hence the value printed out for x will be 1 because it got incremented.
This also applies to Logical OR (||), bitwise OR (|), and boolean OR (|)
Hope this clears up some confusion.
运营商 &&和||是短路的,这意味着如果左侧表达式的值足以确定结果,它们将不会计算右侧表达式。
The operators && and || are short-circuiting, meaning they will not evaluate their right-hand expression if the value of the left-hand expression is enough to determine the result.
&和 |提供与 && 相同的结果和||运营商。不同之处在于它们总是评估表达式的两边,其中 as &&和||停止评估第一个条件是否足以确定结果。
& and | provide the same outcome as the && and || operators. The difference is that they always evaluate both sides of the expression where as && and || stop evaluating if the first condition is enough to determine the outcome.
在 Java 中,单个运算符 &、|、^、!取决于操作数。如果两个操作数都是整数,则执行按位运算。如果两者都是布尔值,则执行“逻辑”运算。
如果两个操作数不匹配,则会引发编译时错误。
双运算符 &&、||其行为与单个操作数类似,但两个操作数都必须是条件表达式,例如:
if (( a < 0 ) && ( b < 0 )) { ... } 或类似的,
if (( a < 0 ) || ( b < 0 )) { ... }
来源:java 编程语言第 4 版
In Java, the single operators &, |, ^, ! depend on the operands. If both operands are ints, then a bitwise operation is performed. If both are booleans, a "logical" operation is performed.
If both operands mismatch, a compile time error is thrown.
The double operators &&, || behave similarly to their single counterparts, but both operands must be conditional expressions, for example:
if (( a < 0 ) && ( b < 0 )) { ... } or similarly,
if (( a < 0 ) || ( b < 0 )) { ... }
source: java programming lang 4th ed
&
和|
是整型上的按位运算符(例如int
): http://download.oracle.com/javase/tutorial/java/nutsandbolts/op3.html&& ;
和||
仅对布尔值进行操作(并且短路,正如其他答案已经说过的那样)。&
and|
are bitwise operators on integral types (e.g.int
): http://download.oracle.com/javase/tutorial/java/nutsandbolts/op3.html&&
and||
operate on booleans only (and short-circuit, as other answers have already said).也许知道按位 AND 和按位 OR 运算符总是在同一表达式中使用条件 AND 和条件 OR 之前计算会很有用。
Maybe it can be useful to know that the bitwise AND and bitwise OR operators are always evaluated before conditional AND and conditional OR used in the same expression.
&& ; ||是逻辑运算符....短路
& ; |是布尔逻辑运算符...非短路
转向表达式执行的差异。位运算符对两边进行计算,而不管左边的结果如何。但在使用逻辑运算符计算表达式的情况下,右侧表达式的计算取决于左侧条件。
例如:
这将打印 i=26 ; j=25,由于第一个条件为假,因此无论右侧条件如何,结果都是假,因此右侧条件被绕过。(短路)
但是,这将打印 i=26; j=26,
&& ; || are logical operators.... short circuit
& ; | are boolean logical operators.... Non-short circuit
Moving to differences in execution on expressions. Bitwise operators evaluate both sides irrespective of the result of left hand side. But in the case of evaluating expressions with logical operators, the evaluation of the right hand expression is dependent on the left hand condition.
For Example:
This will print i=26 ; j=25, As the first condition is false the right hand condition is bypassed as the result is false anyways irrespective of the right hand side condition.(short circuit)
But, this will print i=26; j=26,
如果计算涉及布尔 & 运算符的表达式,则会计算两个操作数。然后&运算符应用于操作数。
当计算涉及 && 运算符的表达式时,将计算第一个操作数。如果第一个操作数的计算结果为 false,则跳过第二个操作数的计算。
如果第一个操作数返回 true 值,则计算第二个操作数。如果第二个操作数返回 true 值,则 &&然后将运算符应用于第一和第二操作数。
类似 |和||。
If an expression involving the Boolean & operator is evaluated, both operands are evaluated. Then the & operator is applied to the operand.
When an expression involving the && operator is evaluated, the first operand is evaluated. If the first operand evaluates to false, the evaluation of the second operand is skipped.
If the first operand returns a value of true then the second operand is evaluated. If the second operand returns a value of true then && operator is then applied to the first and second operands.
Similar for | and ||.
虽然基本区别在于
&
主要用于long
、int
或byte
上的按位运算,其中可用于某种掩码,即使您使用它而不是逻辑&&
,结果也可能有所不同。在某些情况下,差异更为明显:
第一点非常简单,它不会导致错误,但需要更多时间。如果一个条件语句中有多个不同的检查,请将那些成本较低或更有可能失败的检查放在左侧。
对于第二点,请参阅此示例:
对于
null
失败,因为计算第二个表达式会产生NullPointerException
。逻辑运算符&&
是惰性运算符,如果左操作数为假,则无论右操作数是什么,结果都是假。第三点的示例 - 假设我们有一个使用数据库的应用程序,没有任何触发器或级联。在删除建筑物对象之前,我们必须将部门对象的建筑物更改为另一栋。我们还假设操作状态以布尔值形式返回(true = 成功)。然后:
这会计算两个表达式,从而执行建筑物拆除,即使部门更新由于某种原因失败。使用
&&
时,它会按预期工作,并在第一次失败后停止。至于
a || b
,相当于!(!a && !b)
,如果a
为true则停止,无需更多解释。While the basic difference is that
&
is used for bitwise operations mostly onlong
,int
orbyte
where it can be used for kind of a mask, the results can differ even if you use it instead of logical&&
.The difference is more noticeable in some scenarios:
First point is quite straightforward, it causes no bugs, but it takes more time. If you have several different checks in one conditional statements, put those that are either cheaper or more likely to fail to the left.
For second point, see this example:
This fails for
null
, as evaluating the second expression produces aNullPointerException
. Logical operator&&
is lazy, if left operand is false, the result is false no matter what right operand is.Example for the third point -- let's say we have an app that uses DB without any triggers or cascades. Before we remove a Building object, we must change a Department object's building to another one. Let's also say the operation status is returned as a boolean (true = success). Then:
This evaluates both expressions and thus performs building removal even if the department update failed for some reason. With
&&
, it works as intended and it stops after first failure.As for
a || b
, it is equivalent of!(!a && !b)
, it stops ifa
is true, no more explanation needed.