TypeError: 'NoneType' object is not subscriptable (tested)

TypeError: 'NoneType' object is not subscriptable (and its siblings — not iterable, not callable, no len()) all mean the same root problem as 'NoneType' object has no attribute: a variable you expected to hold a real value is None. The difference is which operation you tried on it — indexing with [], looping with for, or calling with () each produce their own distinct TypeError wording instead of AttributeError.

1. Eight operations, eight different messages

Python's error message depends on exactly which operation failed on None, not just that it failed:

Operation on NoneExact error (Python 3.13.5)
x[0]TypeError: 'NoneType' object is not subscriptable
for i in x:TypeError: 'NoneType' object is not iterable
x()TypeError: 'NoneType' object is not callable
int(x)TypeError: int() argument must be a string, a bytes-like object or a real number, not 'NoneType'
len(x)TypeError: object of type 'NoneType' has no len()
5 + xTypeError: unsupported operand type(s) for +: 'int' and 'NoneType'
"a" in xTypeError: argument of type 'NoneType' is not iterable

All eight share one cause: something assigned None to a variable that the rest of the code assumes is a list, dict, string, number, or function.

2. "not subscriptable" means someone used [...] on a plain value

The most common single case: indexing the result of a function that forgot a return, or a dict lookup via .get() that didn't find a key:

>>> def no_return(): pass
>>> r = no_return()
>>> r[0]
TypeError: 'NoneType' object is not subscriptable

>>> x = None
>>> x[0]
TypeError: 'NoneType' object is not subscriptable

This is distinct from IndexError: list index out of range, which means you do have a real list, but asked for a position past its length. "not subscriptable" means you don't have a list (or dict, or anything supporting []) at all — you have None (or occasionally an int or other non-container type).

3. "not iterable" and "not callable" follow the same pattern

>>> x = None
>>> for i in x: pass
TypeError: 'NoneType' object is not iterable

>>> x()
TypeError: 'NoneType' object is not callable

"not callable" is a distinctive one worth knowing by sight: it almost always means a variable name shadowed a function. A classic example is accidentally reassigning a built-in or your own function name, like writing list = get_items() and later calling list() — except here list is now whatever get_items() returned, not the built-in.

4. Arithmetic and len() report the type pairing, not just "NoneType"

>>> 5 + None
TypeError: unsupported operand type(s) for +: 'int' and 'NoneType'
>>> len(None)
TypeError: object of type 'NoneType' has no len()
>>> int(None)
TypeError: int() argument must be a string, a bytes-like object or a real number, not 'NoneType'

These three are more verbose because they come from different code paths internally (operator overloading, the len() protocol, and type constructors), but the diagnosis is identical: a None ended up where a number, sized container, or convertible value was expected.

5. Where the None almost always comes from

6. Fix checklist

For the attribute-access sibling of this error family (.append(), .strip(), etc. instead of [], for, or ()), see AttributeError: 'NoneType' object has no attribute.

Frequently asked questions

What is the difference between 'not subscriptable' and IndexError?

'NoneType' object is not subscriptable means the variable isn't a list/dict/sequence at all - it's None, so [] doesn't apply. IndexError: list index out of range means you do have a real list, but the index you used is past its length. Different problems, different fixes.

Why does TypeError: 'NoneType' object is not callable happen?

It means code tried to call a variable with () as if it were a function, but the variable is actually None. The most common cause is a variable name that shadows a function - for example reassigning a variable to the result of calling the function, then calling that result again by the same name.

Why do int(None) and len(None) have longer error messages than x[0]?

They come from different internal mechanisms: int() goes through type conversion, len() goes through Python's length protocol, and both report what type combination failed rather than a short 'not X-able' phrase. The diagnosis is the same in all cases: a None value reached code expecting something else.

How is this related to AttributeError: 'NoneType' object has no attribute?

They're the same root cause (a None where a real value was expected) producing different exceptions depending on the operation: method/attribute access (.foo) raises AttributeError, while indexing ([]), iteration (for), and calling (()) raise TypeError with their own specific wording.

How do I find where a None value came from?

Read the traceback's line number and look at the assignment just above it - usually a function call, a dict.get(), or an API/database result. Split chained calls onto separate lines while debugging so each step has its own line number to blame.

Written with AI assistance. Measured on 2026-10-03 with Python 3.13.5 on Linux using plain python3 one-liners. Every error below is copy-pasted output, not paraphrased. PlainHeaders is our extension; Python is free.