Are not
and !
synonyms, or are they evaluated differently?
-
1See also https://stackoverflow.com/questions/21060234/ruby-operator-precedence-table – Tim Abell Aug 09 '19 at 14:03
3 Answers
They are almost synonymous, but not quite. The difference is that !
has a higher precedence than not
, much like &&
and ||
are of higher precedence than and
and or
.
!
has the highest precedence of all operators, and not
one of the lowest, you can find the full table at the Ruby docs.
As an example, consider:
!true && false
=> false
not true && false
=> true
In the first example, !
has the highest precedence, so you're effectively saying false && false
.
In the second example, not
has a lower precedence than true && false
, so this "switched" the false
from true && false
to true
.
The general guideline seems to be that you should stick to !
, unless you have a specific reason to use not
. !
in Ruby behaves the same as most other languages, and is "less surprising" than not
.

- 5,632
- 2
- 17
- 24
-
8I have used 'not' in the past to make negated conditionals easier to read. Meaning if the entirety of the conditional should be negated I felt comfortable using 'not' rather than '!'. I like it when my code reads like inglush – jaydel Jul 11 '16 at 18:17
-
-
1@Jacob, yes, definitely. `unless` is just not really favored in the ruby world. The general consensus is that it just gets in the way when `!` works just as well in most situations. I'm sure there are cases where unless may be more expressive, but I steer clear. – Brennan Nov 27 '17 at 22:29
-
8I disagree that `unless` is disfavored. [The closest thing we have to a consensus](https://github.com/rubocop-hq/ruby-style-guide#unless-for-negatives) says otherwise. – Adam Lassek Jun 07 '18 at 16:29
-
2Just wanted to share an example of how surprising `not` can be. In Python, I sometimes assign booleans to variables to make if-statements easier to read. That might mean using the pattern `x = not y`, where y is something complex. In Ruby, `x = !y` works, but `x = not y` gets `syntax error, unexpected tIDENTIFIER, expecting '('`. The precedence order means this needs parentheses around the right of the assignment op to work: `x = (not y)`. – S. Kirby Oct 04 '18 at 18:00
An easy way to understand the not
operator is by looking at not true && false
as being equivalent to !(true && false)

- 191
- 1
- 6
I have an RSpec-driven example here: Ruby's not keyword is not not but ! (not)
In essence:
- They differ in precedence
- They are not aliases
!
can be overriden, whereasnot
cannot be overriden- when you override
!
thennot
will be overriden too, hence it must be using!
under the hood

- 1,020
- 13
- 28