In Python, everything is an object stored in memory. While Python handles memory management automatically (unlike C or C++), there are times when you need to inspect memory addresses for debugging, optimizing performance, or verifying if two variables point to the same object.
This guide explains how to retrieve memory addresses using the built-in id() function, convert them to hexadecimal format, and check for object identity.
Understanding Memory Addresses
A memory address is a unique identifier (an integer) representing the specific location in your computer's RAM where an object is stored. In the standard CPython implementation, the address returned by Python corresponds to the actual memory address of the object structure.
- Uniqueness: No two objects with overlapping lifetimes can have the same ID.
- Constancy: An object's ID never changes once created.
Method 1: Using the id() Function (Standard)
The most direct way to get a memory address is the built-in id() function. It returns the address as a base-10 integer.
x = 42
address = id(x)
print(f"Value: {x}")
print(f"Memory Address (Decimal): {address}")Output (will vary every run):
Value: 42
Memory Address (Decimal): 140541345023504Method 2: Converting to Hexadecimal
Memory addresses are conventionally represented in hexadecimal (base-16) format in low-level programming and debugging tools. You can convert the integer returned by id() using the hex() function.
data = [1, 2, 3]
dec_addr = id(data)
hex_addr = hex(dec_addr)
print(f"List: {data}")
print(f"Decimal Address: {dec_addr}")
print(f"Hex Address: {hex_addr}")Output:
List: [1, 2, 3]
Decimal Address: 140425209473280
Hex Address: 0x7fb74aba6900Method 3: Checking Object Identity (is operator)
While id() gives you the number, you rarely need to compare the numbers manually. To check if two variables point to the same memory address, use the is operator.
a is breturnsTrueifid(a) == id(b).a == breturnsTrueif the contents are equal.
list_a = [10, 20]
list_b = list_a # list_b references the SAME object as list_a
list_c = [10, 20] # list_c is a NEW object with the same content
print(f"A address: {hex(id(list_a))}")
print(f"B address: {hex(id(list_b))}")
print(f"C address: {hex(id(list_c))}")
print(f"A is B? {list_a is list_b}") # True (Same address)
print(f"A is C? {list_a is list_c}") # False (Different address)
print(f"A == C? {list_a == list_c}") # True (Same content)Output:
A address: 0x7fef8b666900
B address: 0x7fef8b666900
C address: 0x7fef8b679400
A is B? True
A is C? False
A == C? TrueCommon Pitfall: Small Integer Caching
Python performs memory optimization for small integers (typically between -5 and 256). These objects are pre-allocated and cached. This means two separate assignments of 100 will point to the same memory address, whereas two assignments of 1000 might not (depending on how the code is executed).
a = 100
b = 100
print(f"100 is 100? {a is b}") # True
x = 257
y = 257
print(f"257 is 257? {x is y}") Output:
100 is 100? True
257 is 257? TrueConclusion
To check memory addresses in Python:
- Use
id(obj)to get the unique integer identifier (memory address). - Use
hex(id(obj))to view the address in the standard hexadecimal format. - Use
a is bto check if two variables refer to the exact same object in memory.