Understanding Class Variables and Instance Variables in Python
This article explains the differences between class variables and instance variables in object‑oriented programming, illustrates their characteristics with clear Python examples, and demonstrates advanced patterns such as counting instances, default values, constants, static data, configuration options, and polymorphic behavior.
Class variables and instance variables are two fundamental concepts in object‑oriented programming. The main distinction lies in their scope and lifecycle: instance variables belong to each object, while class variables are shared across all instances of the class.
Instance Variables
Instance variables are defined inside class methods (typically __init__ ) and each object gets its own copy. They store state that can vary independently between objects.
class Person:
def __init__(self, name, age):
self.name = name # instance variable
self.age = age # instance variable
# create objects
person1 = Person("Alice", 25)
person2 = Person("Bob", 30)
# modify an instance variable
person1.age = 26
# access instance variables
print(person1.name) # Alice
print(person1.age) # 26
print(person2.name) # Bob
print(person2.age) # 30In this example, name and age are instance variables; each Person object maintains its own values.
Class Variables
Class variables are defined in the class body outside any method. All instances share a single copy, making them suitable for shared configuration or constants.
class Person:
species = "Human" # class variable
def __init__(self, name, age):
self.name = name # instance variable
self.age = age # instance variable
# create objects
person1 = Person("Alice", 25)
person2 = Person("Bob", 30)
# access class variable
print(Person.species) # Human
print(person1.species) # Human
print(person2.species) # Human
# modify class variable
Person.species = "Homo sapiens"
print(Person.species) # Homo sapiens
print(person1.species) # Homo sapiens
print(person2.species) # Homo sapiensHere species is a class variable shared by all Person objects; changing it affects every instance.
Mixed Use Example
Often a class uses both kinds of variables, e.g., a class variable for a global raise factor and instance variables for personal data.
class Employee:
raise_amount = 1.04 # class variable
def __init__(self, first, last, pay):
self.first = first # instance variable
self.last = last # instance variable
self.email = f"{first}.{last}@company.com" # instance variable
self.pay = pay # instance variable
def apply_raise(self):
self.pay = int(self.pay * Employee.raise_amount)
# create objects
emp_1 = Employee("John", "Doe", 60000)
emp_2 = Employee("Jane", "Smith", 70000)
# change class variable
Employee.raise_amount = 1.05
# apply raise
emp_1.apply_raise()
emp_2.apply_raise()
# access instance data
print(emp_1.email) # [email protected]
print(emp_1.pay) # 63000
print(emp_2.email) # [email protected]
print(emp_2.pay) # 73500In this snippet raise_amount is shared, while each employee keeps its own personal attributes.
Advanced Patterns Using Class Variables
1. Counting Instances
class Person:
count = 0 # class variable, records instance count
def __init__(self, name, age):
self.name = name
self.age = age
Person.count += 1
person1 = Person("Alice", 25)
person2 = Person("Bob", 30)
person3 = Person("Charlie", 35)
print(Person.count) # 32. Default Values
class Student:
default_major = "Undeclared"
def __init__(self, name, major=None):
self.name = name
self.major = major or Student.default_major
student1 = Student("Alice", "Computer Science")
student2 = Student("Bob")
print(student1.name, student1.major) # Alice Computer Science
print(student2.name, student2.major) # Bob Undeclared3. Defining Constants
class Circle:
PI = 3.14159
def __init__(self, radius):
self.radius = radius
def area(self):
return Circle.PI * self.radius ** 2
c1 = Circle(5)
c2 = Circle(10)
print(c1.area()) # 78.53975
print(c2.area()) # 314.1594. Storing Static Data
class ProductCatalog:
catalog = {"Apple": 10, "Banana": 5, "Orange": 7}
def get_price(self, product_name):
return self.catalog.get(product_name)
catalog = ProductCatalog()
print(catalog.get_price("Apple")) # 10
print(catalog.get_price("Banana")) # 5
print(catalog.get_price("Pear")) # None5. Configuration Options
class Settings:
debug_mode = False
def toggle_debug_mode(self):
Settings.debug_mode = not Settings.debug_mode
settings = Settings()
print(Settings.debug_mode) # False
settings.toggle_debug_mode()
print(Settings.debug_mode) # True
settings.toggle_debug_mode()
print(Settings.debug_mode) # False6. Polymorphism with Class and Instance Variables
class Vehicle:
wheels = 4
def __init__(self, color):
self.color = color
def description(self):
return f"A {self.color} vehicle with {self.wheels} wheels."
class Car(Vehicle):
def __init__(self, color, model):
super().__init__(color)
self.model = model
def description(self):
return f"A {self.color} {self.model} car with {self.wheels} wheels."
class Motorcycle(Vehicle):
wheels = 2 # overrides base class variable
def __init__(self, color, make):
super().__init__(color)
self.make = make
def description(self):
return f"A {self.color} {self.make} motorcycle with {self.wheels} wheels."
car = Car("Red", "Toyota")
motorcycle = Motorcycle("Blue", "Honda")
print(car.description()) # A Red Toyota car with 4 wheels.
print(motorcycle.description()) # A Blue Honda motorcycle with 2 wheels.These examples show how class variables can be used for shared state, defaults, constants, static resources, configuration, and even to influence polymorphic behavior, while instance variables preserve per‑object state.
Conclusion
Instance variables give each object its own independent data, whereas class variables provide a single shared value across all objects, making them ideal for global settings, counters, constants, and shared resources in Python programs.
Test Development Learning Exchange
Test Development Learning Exchange
How this landed with the community
Was this worth your time?
0 Comments
Thoughtful readers leave field notes, pushback, and hard-won operational detail here.