NoSingleLogicAndObserved

& is only a bitwise AND
& for boolean operands is a logical AND
CorrectionHere is what's right.
While &
can be a bitwise AND, &
can also be used as a logical AND between bool
operands.
That’s because in Python, booleans are actually integers: False
is 0
, and True
is 1
.
a = False
b = True
c = a and b # logical AND (short-circuit)
a = False
b = True
c = a & b # logical AND
a = 1
b = 3
c = a & b # bitwise AND
Note that &
is an eager logical AND. “Eager” means it always evaluates both operands before producing a value.
On the other hand, and
is a short-circuit logical AND. It first evaluates the left operand; if that is False
, then it does not evaluate the right operand and simply produces False
. This can be very useful for conditions like the following, because it prevents ZeroDivisionError
that would have been raised if the right operand had to be evaluated:
if lst != [] and sum(lst) / len(lst) > 42:
...
SymptomsHow do you know your students might have this misconception?
If students claim that &
is a bitwise AND, and and
is a logical AND, then they probably also believe that &
cannot work with bool
operands.
ValueHow can you build on this misconception?
It can be instructive to think about a situation where the difference between &
and and
is observable. Consider the following example:
def f():
print("hi")
return False
Evaluating f() and f()
will print “hi” only once, because the second call to f()
is not evaluated due to short-circuiting.
On the other hand, evaluating f() & f()
will print “hi” twice, because both calls to f()
are evaluated regardless of the result of the first call.