MemoryError
The data does not fit: stream it, chunk it, or store it more compactly — catching MemoryError is a last resort, not a fix.
MemoryError(*args)
Raised by
building huge lists/strings, f.read() of a giant file, loading big datasets whole
Message
usually empty — just MemoryError
Quick fix
process in chunks / generators instead of all at once
Watch out
on Linux the OS may kill the process ("Killed") before Python can raise
Constructor
| Name | Type | Required | Description |
|---|---|---|---|
| *args | object | no | Optional message. Allocation failures inside CPython usually raise it with no arguments. |
Attributes
| Attribute | Type | Meaning |
|---|---|---|
| args | tuple | Usually () — the interpreter rarely attaches a message. Libraries (NumPy, pandas) raise their own subclasses with a size in the message. |
Common patterns
Stream a file line by line
Iterating a file keeps one line in memory at a time, whatever the file size.
total = 0 with open('huge.log', encoding='utf-8') as f: for line in f: if 'ERROR' in line: total += 1
Fixed-size chunks for binary data
Hash or copy files of any size with a small, constant buffer.
import hashlib h = hashlib.sha256() with open('disk.img', 'rb') as f: for chunk in iter(lambda: f.read(1 << 20), b''): h.update(chunk)
Generator instead of list
A generator expression produces items on demand; sum() never needs the whole sequence.
total = sum(x * x for x in range(10**9))
Last-resort handler
Free the big object first, then report. Keep the handler tiny — it may itself need memory.
try: table = build_table(rows) except MemoryError: table = None raise SystemExit('not enough memory for this input; try --chunked')
Examples
1. Raise it
raise MemoryError
Returns
MemoryError2. Usually no message
str(MemoryError())
Returns
''3. Catch it like any Exception
try:
raise MemoryError
except MemoryError as e:
caught = repr(e)
caught
Returns
'MemoryError()'4. Absurd sizes fail earlier — as OverflowError
[None] * 10**20
Returns
OverflowError: cannot fit 'int' into an index-sized integer5. A generator holds nothing up front
sum(x for x in range(10**6))
Returns
4999995000006. Not a RuntimeError
issubclass(MemoryError, RuntimeError), issubclass(MemoryError, Exception)
Returns
(False, True)Pitfalls
1. Materialising a list you only iterate once
A list comprehension builds every element before sum() starts; a generator expression builds one at a time. Same answer, a tiny fraction of the memory for large ranges.
List first
sum([x * x for x in range(1000)])
332833500
Generator
sum(x * x for x in range(1000))
332833500
2. read() on a file of unknown size
f.read() loads the entire file into one string. Iterate the file instead so memory use stays flat.
read() everything
with open('log.txt', 'w') as f: f.write('ok\nERROR x\nok\n') with open('log.txt') as f: n = f.read().count('ERROR') n
1
Stream lines
with open('log.txt', 'w') as f: f.write('ok\nERROR x\nok\n') with open('log.txt') as f: n = sum('ERROR' in line for line in f) n
1
When to use
Use it
- A last-resort handler that frees memory and reports a clear error
- Raising it from a C extension or custom allocator when allocation fails
Reach for something else
- Treating it as normal control flow — the process may be too starved to recover
- Growing a structure until MemoryError to "find the limit"
Notes
Linux OOM killer
With memory overcommit, allocations may succeed and the kernel kills the process later ("Killed", exit code 137) — no exception at all
32-bit Python
A 32-bit interpreter hits MemoryError around 2–4 GB regardless of installed RAM; check with struct.calcsize("P") * 8
NumPy
Raises a private MemoryError subclass (_ArrayMemoryError) with "Unable to allocate … for an array with shape …" — except MemoryError catches it
FAQ
Triggering a real MemoryError means actually exhausting memory, which would freeze your browser tab or a reader's machine, and the point where it happens depends on RAM, the OS and other processes. The examples raise and catch it directly instead, and show the safe patterns that prevent it.