Python Operator Precedence and Associativity Guide
Master Python operator precedence and associativity with a full table, five traced examples, and the right-to-left rule that makes 2 ** 3 ** 2 return 512.
Python evaluates operators in a strict priority order, and that order explains why 2 ** 3 ** 2 returns 512, not 64.
This is operator precedence: the rule that determines which operator Python processes first when an expression contains more than one. Get it wrong and you get silent arithmetic errors that pass syntax checks and produce the wrong answer. No interpreter warning. Just a bad result.
What Operator Precedence Means in Python
Consider 5 + 3 * 2. The result is 11, not 16.
Python applies multiplication before addition because * sits higher in the precedence table than +. The multiplication 3 * 2 = 6 runs first, then 5 + 6 = 11. If you need the addition to run first, parentheses enforce that: (5 + 3) * 2 = 16. Parentheses win every time.
This is the core rule: operators with higher precedence run before operators with lower precedence. Parentheses override everything else. Every other relationship is determined by where the operator sits in Python’s precedence hierarchy.
The rule applies across all operator types together. A bitwise shift (<<) has higher precedence than a comparison (==), which has higher precedence than logical and. When an expression mixes types, precedence is the only thing that determines evaluation sequence.
Python Operator Precedence Table
The Python 3 reference documentation defines the complete precedence table. The table below runs from highest priority to lowest:
| Operator(s) | Description |
|---|---|
(), [], {} | Parentheses, list/dict/set literals (highest) |
** | Exponentiation |
+x, -x, ~x | Unary plus, unary minus, bitwise NOT |
*, /, //, %, @ | Multiplication, division, floor division, modulo, matrix multiply |
+, - | Addition, subtraction |
<<, >> | Bitwise left shift, right shift |
& | Bitwise AND |
^ | Bitwise XOR |
| | Bitwise OR |
==, !=, <, <=, >, >=, in, not in, is, is not | Comparison operators |
not x | Logical NOT |
and | Logical AND |
or | Logical OR |
x if c else y | Conditional (ternary) expression |
lambda | Lambda expression |
:= | Walrus operator (lowest) |
Two things stand out. First, ** sits well above *, /, +, and -. Exponentiation is not a “stronger multiply”; it sits in its own tier. Second, all comparison operators (==, !=, <, <=, >, >=, in, not in, is, is not) share a single row. They do not have sub-hierarchy among themselves. They chain instead of nesting.
Associativity: Left-to-Right vs Right-to-Left
Precedence tells Python which operator evaluates first when two operators are different. Associativity tells Python which evaluates first when two operators are the same, appearing in sequence.
Left-to-Right: the Default
Almost every Python operator is left-to-right. 10 / 2 / 5 evaluates as (10 / 2) / 5 = 5.0 / 5 = 1.0, not 10 / (2 / 5) = 25.0. The two / operations run left-to-right. Same for +, -, *, //, %, and the bitwise operators.
Right-to-Left: the Exponentiation Exception
Exponentiation reverses the default. 2 ** 3 ** 2 evaluates right-to-left: Python processes 3 ** 2 first, then uses that result as the exponent for the 2.
- Step 1:
3 ** 2 = 9 - Step 2:
2 ** 9 = 512
If Python used left-to-right, the result would be (2 ** 3) ** 2 = 8 ** 2 = 64. It doesn’t.
Comparison Chaining: Neither Left nor Right
Comparison operators do not associate in the normal sense. They chain. According to the Python documentation on comparisons, a < b < c is equivalent to (a < b) and (b < c), with b evaluated only once.
1 < 2 < 3 is not (1 < 2) < 3. It is (1 < 2) and (2 < 3). Both comparisons are checked independently. This Python-specific feature does not exist in C, Java, or most other languages. In C, 1 < 2 < 3 would compute (1 < 2) < 3 = 1 < 3 = 1 (true by coincidence). Python’s version is semantically cleaner.
Five Worked Examples Traced Step by Step
Each example below traces evaluation from the first operator applied to the final result.
Example 1: Mixed Arithmetic
print(5 + 3 * 2)
*has higher precedence than+- Step 1:
3 * 2 = 6 - Step 2:
5 + 6 = 11 - Output:
11
Example 2: Exponentiation Chain (Right-to-Left)
print(2 ** 3 ** 2)
**is right-associative; rightmost exponentiation runs first- Step 1:
3 ** 2 = 9 - Step 2:
2 ** 9 = 512 - Output:
512
Left-to-right would give (2 ** 3) ** 2 = 8 ** 2 = 64. The correct answer is 512.
Example 3: Division Chain (Left-to-Right)
print(10 / 2 / 5)
/is left-associative; leftmost division runs first- Step 1:
10 / 2 = 5.0 - Step 2:
5.0 / 5 = 1.0 - Output:
1.0
Example 4: Logical NOT and Comparison
print(not 5 > 3)
>(comparison) has higher precedence thannot- Step 1:
5 > 3 = True - Step 2:
not True = False - Output:
False
A common misreading is (not 5) > 3. In Python, not 5 evaluates to False because 5 is truthy; False > 3 is technically valid Python but semantically wrong for what the expression means. The correct parse is not (5 > 3).
Example 5: Comparison Chaining
print(1 < 2 < 3)
- Python expands chained comparisons into an
andexpression - Equivalent to:
(1 < 2) and (2 < 3) - Step 1:
1 < 2 = True - Step 2:
2 < 3 = True - Step 3:
True and True = True - Output:
True
The shared middle value (2) is evaluated once. If you write 1 < x() < 3 where x() has a side effect, that side effect happens exactly once.
Two Mistakes That Cost Marks in Assessments
Assuming Exponentiation Is Left-to-Right
Most candidates assume all same-precedence operators run left-to-right. ** breaks that assumption. In a Python MCQ that asks for the output of 2 ** 3 ** 2, the answer choices typically include both 64 and 512. Candidates who apply left-to-right get 64. The correct answer is 512.
The fix: memorise that ** is the one common operator in Python that runs right-to-left. Everything else above not runs left-to-right.
Forgetting not’s Low Precedence
not sits below all comparison operators in the table. not x == y means not (x == y), not (not x) == y. These produce different results when x and y differ. not 5 > 3 means not (5 > 3) = False, as traced above. If you find yourself writing not before a comparison expression, read the table once to confirm which side the not binds to.
Both mistakes appear in Python MCQs in campus assessments. The precedence table is the answer key: when in doubt, look up where each operator sits and work from the highest-precedence one down.
Programs that put these operators to work include a simple calculator in Python, where arithmetic precedence determines the output for every expression the user types, and finding the greatest of three numbers in Python, which chains comparison operators directly. For broader practice across expression types, Python basic programs covers the full operator set. The Armstrong number program uses ** for digit-power calculations, making it a clean test case for the right-to-left rule.
Understanding why 2 ** 3 ** 2 returns 512 makes more sense when you run it yourself and tweak the exponents. TinkerLLM provides a Python sandbox where you can trace operator evaluation live, check your mental model against real output, and work through the full precedence table interactively. Full access is ₹299.
Primary sources
Frequently asked questions
What is the highest-precedence operator in Python?
Parentheses () sit at the top of the precedence table. Any expression inside parentheses evaluates before anything else in the surrounding expression.
Is ** left or right associative in Python?
Exponentiation (**) is right-to-left associative. So 2 ** 3 ** 2 evaluates as 2 ** (3 ** 2) = 512, not (2 ** 3) ** 2 = 64.
What does not 5 > 3 return in Python?
It returns False. Comparison operators have higher precedence than not, so Python evaluates (5 > 3) = True first, then not True = False.
How does Python handle chained comparisons like 1 < 2 < 3?
Python expands chained comparisons into an and expression: (1 < 2) and (2 < 3), which is True and True = True. Each middle value is evaluated only once.
When should I use parentheses in Python expressions?
Use parentheses whenever an expression mixes operator types and the evaluation order is not immediately obvious. They override all other precedence rules and make your intent clear to both Python and the next reader.
What is the walrus operator and where does it fit in precedence?
The walrus operator (:=) assigns a value as part of an expression. It has the lowest precedence in Python, sitting below lambda expressions in the table.
A self-paced playground for building with LLMs.
TinkerLLM is FACE Prep's sister property. A guided environment for shipping real LLM applications, the kind of project that earns a paragraph on your resume, not a line.
Try TinkerLLM (₹299 launch)