I tried to write a++ in Python once and got a SyntaxError pointing at the second plus. The fix was simple, but the explanation was not, and the answer to why Python chose not to ship an increment operator is the kind of detail you only see if you go look at the grammar.

There is no ++ in Python. The replacement is a += 1, an augmented assignment, and below are the cases where the operator behaves differently from what a C, Java, or JavaScript developer would expect.

a++ raises a SyntaxError in Python

Type it in a REPL and Python refuses to parse it:

>>> a = 1
>>> a++
  File "", line 1
    a++
      ^
SyntaxError: invalid syntax

The error lands on the second plus. The tokenizer reads a, then a binary +, then expects the right operand of an addition. It gets another + instead of a value, and parsing stops there.

Pre-increment is not a fix either. ++a is two unary + operators in a row, and unary + is the identity on numbers. The expression returns a unchanged.

>>> a = 1
>>> ++a
1
>>> +(+a)
1

So Python parses a++ as a + (+), which is a syntax error, and ++a as +(+a), which is the same value. Neither does what a C developer means by the symbols.

The replacement is +=

The grammar for += lives in the language reference next to -=, *=, and the rest of the augmented assignment family, and the call site is the same in every case: a += 1.

>>> a = 10
>>> a += 1
>>> a
11
>>> a += 100
>>> a
111

For strings += concatenates, for lists and tuples it appends, and the right-hand side can be any iterable or scalar that the type knows how to add. The same operator works on all of them.

>>> s = 'Hello'
>>> s += ' world'
>>> s
'Hello world'

>>> nums = [1, 2, 3]
>>> nums += [4, 5]
>>> nums
[1, 2, 3, 4, 5]

>>> t = (1, 2)
>>> t += (3,)
>>> t
(1, 2, 3)

Strings do not accept int on the right-hand side. The + is concatenation, and concatenating int to str is the same kind of error you get from a + 1.

>>> s = 'count: '
>>> s += 1
Traceback (most recent call last):
  File "", line 1, in 
TypeError: can only concatenate str (not "int") to str

The right move is f-strings, format, or str(1), not +=.

How += evaluates under the hood

The evaluation order is the difference, and it shows up in the bytecode. A regular assignment computes the right-hand side first, then assigns to the left. An augmented assignment is the opposite: fetch the target first, run the in-place operation on the existing object, then write the result back.

For a mutable type that defines __iadd__, the in-place version mutates the object instead of allocating a new one. The difference is visible if you hold a second reference to the same list, and lists are the simplest type that shows it.

>>> a = [1, 2, 3]
>>> b = a           # b points at the same list
>>> a += [4]        # __iadd__: extends in place
>>> a
[1, 2, 3, 4]
>>> b
[1, 2, 3, 4]       # b sees the change

>>> a = a + [5]     # __add__: builds a new list, rebinds a
>>> a
[1, 2, 3, 4, 5]
>>> b
[1, 2, 3, 4]       # b still points at the old list

An immutable type like tuple or int has no in-place variant, so += always rebinds. The object is replaced, the old one is dropped, and any other reference to it is unaffected.

You can hook the in-place variant in your own classes. The __iadd__ method should return self after mutating in place. If your class does not define it, Python falls back to __add__ and rebinds.

class Counter:
    def __init__(self, n=0):
        self.n = n
    def __iadd__(self, other):
        self.n += other
        return self
    def __repr__(self):
        return f'Counter({self.n})'

>>> c = Counter(10)
>>> c += 5
Counter(15)

If __iadd__ returns NotImplemented, Python delegates to __add__ and the variable gets rebound, just like a tuple. The class decides at runtime whether the operation is in place or not.

Decrement, multiply, and the rest of the family

Every C-style compound operator has a Python equivalent under the augmented assignment grammar. The table covers the ones you will reach for. The grammar is the same for every row: fetch the target, apply the operator in place if the type supports it, store the result.

Intent Python Notes
Increment by 1 a += 1 Works for int, list, str, tuple, Counter
Decrement by 1 a -= 1 No — operator. Mirror of +=
Multiply in place a *= k For lists, repeats. For numpy arrays, elementwise
Append iterable a += iter Equivalent to a.extend(iter) for lists
Bitwise left shift a <<= k For ints
Modulo a %= k For ints and Decimal

Frequently asked questions

Why doesn’t Python have a ++ operator?

The language designers decided the augmented assignment += covers the same need without adding a unary operator that does not compose with the rest of Python’s grammar. a++ is parsed as a + (+), which is a syntax error. ++a parses as +(+a), which is the identity.

Is a += 1 the same as a = a + 1?

The result is the same. The evaluation order is not. += tries __iadd__ first and mutates the existing object in place if the type supports it. a = a + 1 always calls __add__ and rebinds. For ints and tuples the difference does not matter. For lists and numpy arrays it does, because other references see the change.

Can I write a custom ++ for my class?

Define __iadd__ on the class. The method should mutate the instance and return self. If __iadd__ returns NotImplemented, Python falls back to __add__ and the variable gets rebound.

Share.
Leave A Reply