Boolean Logical Operators and Boolean Conditional Logical Operators
I’m often amazed that most programmer don’t know that in C# and in Java you can use the simple & and | as logical operators. It seems than most people don’t event know that they exist!
But what’s the difference between these simple and double logical operators?
Back To Basics
Let’s see in the C# language specifications:
The result of
x
&
y
istrue
if bothx
andy
aretrue
. Otherwise, the result isfalse
.The result of
x
|
y
istrue
if eitherx
ory
istrue
. Otherwise, the result isfalse
.
Now let’s have a look in Java language specifications:
For
&
, the result value istrue
if both operand values aretrue
; otherwise, the result isfalse
.For
|
, the result value isfalse
if both operand values arefalse
; otherwise, the result istrue
.
It’s pretty clear, it does what most of the people would expect them to do, and and or operations.
But, then, what are those && and || that most developers use everywhere, wasting bytes like there’s now tomorrow?
Again, specifications are there to give full explanations.
In C#:
The
&&
and||
operators are conditional versions of the&
and|
operators:
- The operation
x
&&
y
corresponds to the operationx
&
y
, except thaty
is evaluated only ifx
istrue
.- The operation
x
||
y
corresponds to the operationx
|
y
, except thaty
is evaluated only ifx
isfalse
.
And in Java:
The
&&
operator is like&
(§15.22.2), but evaluates its right-hand operand only if the value of its left-hand operand istrue
.The
||
operator is like|
(§15.22.2), but evaluates its right-hand operand only if the value of its left-hand operand isfalse
.
Tadaaaam! Now it makes perfect sense, doesn’t it? These operators that most of the people use everywhere are smart and only evaluate the right-side if it is of any use (if left-hand side is true for and, if left-hand side is false for or).
So, let’s give a small example of how this can be useful. Let’s pretend you have an object that has a member that can be null. With these operators, you can test it without any fear of the dreaded NullReferenceException or NullPointerException. Here is a small piece of C# code that shows the point:
var p = new Parent { Name = "Father" }; p.Childs = new Person[] { new Person() { Name = "Son" } }; if (p.Childs != null && p.Childs.ElementAt(0).Name != null) { Console.WriteLine("First Child's name: {0}", p.Childs.ElementAt(0).Name); }
If Child collection was left null, this code would still work even though p.Childs.ElementAt(0) would normally throw an ArgumentNullException. As p.Childs != null returns false, the right-hand operand is not evaluated so no exception is thrown.
Now, as you may say “Well in this case, why does it matter? Let’s use && and || everywhere, so we make no mistake!”. Technically, it is true. However, as one of my University teacher said:
Les gens qui utilisent les opérateurs conditionnels booléens partout sont des gens qui ne savent pas ce qu'ils font.
Translation: “Peoples who use conditional logical operators everywhere are peoples that don’t know what they're doing”.
Of course, his point was that you should understand the code you are writing and that you should know when which part of an expression can be evaluated. I have no clue if there is a performance gain when using non conditional operators, nor if there is any compiler optimization of any kind.
The Third Operator
There is also a third operator in both languages: ^.
In C#:
The result of
x
^
y
istrue
ifx
istrue
andy
isfalse
, orx
isfalse
andy
istrue
. Otherwise, the result isfalse
. When the operands are of typebool
, the^
operator computes the same result as the!=
operator.
In Java:
For
^
, the result value istrue
if the operand values are different; otherwise, the result isfalse
.
I’v never seen this operator used. As pointed in C# specification, this operator has the same result as the != operator.
And, of course, it doesn’t make any sense to have a ^^ operator, as both operand have to be evaluated in all the cases…
blog comments powered by Disqus