||
and &&
bind with the precedence that you expect from boolean operators in programming languages (&&
is very strong, ||
is slightly less strong).
and
and or
have lower precedence.
For example, unlike ||
, or
has lower precedence than =
:
> a = false || true
=> true
> a
=> true
> a = false or true
=> true
> a
=> false
Likewise, unlike &&
, and
also has lower precedence than =
:
> a = true && false
=> false
> a
=> false
> a = true and false
=> false
> a
=> true
What's more, unlike &&
and ||
, and
and or
bind with equal precedence.
Notice that because &&
is higher precedence than ||
, the 2nd and 3rd clause are bound together, so there's no need to evaluate either of them once the 1st clause evaluates true:
> !puts(1) || !puts(2) && !puts(3)
1
=> true
But since or
and and
have equal precedence, the left-most and
or or
operator has higher precedence. In this case the or
is left-most so it binds the 1st and 2nd clauses together. Because the second operator is an and
, the 3rd clause must be evaluated to resolve the expression:
> !puts(1) or !puts(2) and !puts(3)
1
3
=> true
Observe that the parentheses force the and
to bind the 2nd and 3rd clauses together, just as if it were an &&
:
> !puts(1) or (!puts(2) and !puts(3))
1
=> true
The weakly-binding and
and or
may be useful for control-flow purposes: see Using "and" and "or" in Ruby.