What does "everything is an object" mean in Python, and why does it matter?

5 minbeginnerfundamentalsobject-modeldata-model

Quick Answer

In Python, **ints, functions, classes, and modules** are all objects with an identity, type, and attributes — there's no primitive/object split like in Java. This means you can pass functions as arguments, attach attributes to a function, inspect a class's `__dict__` at runtime, and treat `type` itself as an object (an instance of `type`). It's the foundation for decorators, introspection, and duck typing.

Detailed Answer

Everything is an object

In Python, 1, "hello", def f(): pass, a class, a module, and even type itself are all objects: each has an identity (id(x)), a type (type(x)), and a set of attributes. There is no distinction between "primitive types" and "reference types" the way there is in Java or C#.

def greet():
    return "hi"

print(type(greet))          # <class 'function'>
print(greet.__name__)       # 'greet'
greet.calls = 0             # you can attach arbitrary attributes to a function
greet.calls += 1

print(type(int))            # <class 'type'>
print(type(type))           # <class 'type'>  -- type is an instance of itself

Why it matters

1. Functions are first-class values. You can store them in variables, put them in lists, pass them as arguments, and return them from other functions — this is what makes decorators, callbacks, and higher-order functions like map/sorted(key=...) work.

2. Classes and types are runtime objects. class Foo: ... executes a statement that creates a type object and binds it to Foo. That's why you can build classes dynamically with type(name, bases, namespace), and why metaclasses (which customize how type builds a class) are possible.

3. Introspection is cheap and universal. Because every object exposes __dict__, __class__, type(), and dir(), generic tooling (debuggers, serializers, ORMs, pytest fixtures) can inspect any object the same way, regardless of whether it's a number, a function, or a user-defined class.

4. It underlies duck typing. Since behavior is just "does this object respond to this attribute/method," Python doesn't need a common base type to treat unrelated objects polymorphically — it just checks capabilities at the point of use.

Interview-ready summary: Python has a single, uniform object model — numbers, functions, classes, and modules are all first-class objects with identity, type, and attributes. That uniformity is why closures, decorators, metaclasses, and duck typing all work through the same mechanism: attribute access and the type system, not special-cased primitive rules.