Advanced Python Objects
Advanced Python Objects
Introduction
Python is an object-oriented programming language that allows the creation and manipulation
of objects. Advanced Python objects involve deeper concepts such as custom objects, special
methods, property decorators, class methods, static methods, and more. These concepts are
crucial for writing more efficient, readable, and maintainable code.
Defining a Class
A class is a blueprint for creating objects (instances). Classes encapsulate data and functions
that operate on the data.
class Person:
def __init__(self, name, age):
self.name = name
self.age = age
def greet(self):
return f"Hello, my name is {self.name} and I am {self.age} years
old."
Creating an Object
Special methods in Python start and end with double underscores (__). They are used to
emulate built-in behavior within user-defined classes.
The following special methods control how an object interacts with + , * , ** , and other
mathematical operators.
Example
class Vector:
def __init__(self, x, y):
self.x = x
self.y = y
def __repr__(self):
return f"Vector({self.x}, {self.y})"
def __len__(self):
return int((self.x**2 + self.y**2) ** 0.5)
v1 = Vector(3, 4)
v2 = Vector(1, 2)
v3 = v1 + v2
3. Property Decorators
Property decorators provide a way to manage the access to instance attributes. They are
useful for adding getter, setter, and deleter functionality.
class Circle:
def __init__(self, radius):
self._radius = radius
@property
def radius(self):
return self._radius
@radius.setter
def radius(self, value):
if value < 0:
raise ValueError("Radius cannot be negative")
self._radius = value
@property
def area(self):
return 3.14159 * self._radius ** 2
c = Circle(5)
print(c.radius) # Output: 5
print(c.area) # Output: 78.53975
c.radius = 3
print(c.area) # Output: 28.27431
Class methods and static methods are different ways to define methods that are not bound to
instance objects.
Class Methods
Class methods are bound to the class and not the instance of the class. They can modify class
state that applies across all instances. A class method receives the class as an implicit first
argument, just like an instance method receives the instance
class MyClass:
class_variable = 0
@classmethod
def increment_class_variable(cls):
cls.class_variable += 1
MyClass.increment_class_variable()
print(MyClass.class_variable) # Output: 1
Static Methods
Static methods are bound to the class and not the instance of the class. They do not modify
object or class state.
class MathOperations:
@staticmethod
def add(x, y):
return x + y
Inheritance allows one class to inherit attributes and methods from another class.
Polymorphism allows methods to do different things based on the object it is acting upon.
Inheritance
Syntax:
class DerivedClass(BaseClass):
# Class definition
Single Inheritance
class child(parent):
# child class
def func2(self): # we include the parent class
print("Hello Child") # as an argument in the child
# class
# Driver Code
test = child() # object created
test.func1() # parent method called via child object
test.func2()
Multiple Inheritance
# Driver Code
test = child() # object created
test.func1() # parent1 method called via child
test.func2() # parent2 method called via child instead of
parent3
test.func3(
Multilevel Inheritance
# Driver Code
test = child() # object created
test.func1() # 3rd level calls 1st level
test.func2() # 3rd level calls 2nd level
test.func3()
Polymorphism
def info(self):
print(f"I am Liquid Form. I am {self.name}. and my formula is {self.formula}")
def property(self):
print("I am clear and light form")
class Solid:
def __init__(self, name, formula):
self.name = name
self.formula = formula
def info(self):
print(f"I am Solid Form. I am {self.name}. and my formula is {self.formula}")
def property(self):
print("I can be transparent or clear or completely opaque")
Here, we create two classes: Liquid and Solid. Here, we define info() and property() for both
of them. These functions work differently depending on which class object you call.
and attributes of a parent class to a child class. The parent class is also known as base class,
class F1():
def run(self):
print("Win")
class F2(F1):
def run(self):
print("2nd place - F2 cars are slower than F1 cars")
class F3(F1):
def run(self):
print("3rd place - F3 cars are slower than F2 and F1 cars")
obj_F1 = F1()
obj_F2 = F2()
obj_F3 = F3()
obj_F1.run()
obj_F2.run()
obj_F3.run()
Win
2nd place - F2 cars are slower than F1 cars
3rd place - F3 cars are slower than F2 and F1 cars
Here, we first defined our F1 class and then passed it as a parameter in the F2 class. Each time
we called the run() function on objects of F1, F2 and F3 class, the inheritance and method
6. Encapsulation
Encapsulation restricts access to methods and variables to prevent data from being modified
directly. This is achieved using private and protected access modifiers.
The members of a class that are declared public are easily accessible from any part of the
program. All data members and member functions of a class are public by default.
The members of a class that are declared protected are only accessible to a class derived
from it. Data members of a class are declared protected by adding a single underscore ‘_’
symbol before the data member of that class.
The members of a class that are declared private are accessible within the class only,
private access modifier is the most secure access modifier. Data members of a class are
declared private by adding a double underscore ‘__’ symbol before the data member of that
class.
class Super:
# constructor
def __init__(self, var1, var2, var3):
self.var1 = var1
self._var2 = var2
self.__var3 = var3
# derived class
class Sub(Super):
# constructor
def __init__(self, var1, var2, var3):
Super.__init__(self, var1, var2, var3)