DEV Community

M.T.Ramkrushna
M.T.Ramkrushna

Posted on

4. PYTHON ESSENTIALS FOR AI/ML (Advanced OOP)

1. Class Methods (@classmethod)

What it is

A method that belongs to the class, not an individual object.
It receives cls instead of self.

When it's used

  • Creating alternative constructors
  • Tracking class-level data

Example

class Employee:
    company = "OpenAI"
    count = 0

    def __init__(self, name):
        self.name = name
        Employee.count += 1

    @classmethod
    def total_employees(cls):
        return cls.count

print(Employee.total_employees())  # 0
e1 = Employee("Ali")
e2 = Employee("Sara")
print(Employee.total_employees())  # 2
Enter fullscreen mode Exit fullscreen mode

2. Static Methods (@staticmethod)

What it is

A method inside the class but does NOT access class or instance data.

When used?

  • Utility/helper methods
  • Math or formatting functions

Example

class MathTool:
    @staticmethod
    def add(a, b):
        return a + b

print(MathTool.add(3, 4))
Enter fullscreen mode Exit fullscreen mode

3. Dunder (Magic) Methods

These are special methods starting with __.
They let you customize how your object behaves.

Common ones

Magic method Purpose
__init__ constructor
__str__ object to string
__len__ length
__add__ overloading + operator
__getitem__ indexing
__call__ make object callable

Example: custom print

class Person:
    def __init__(self, name):
        self.name = name

    def __str__(self):
        return f"Person: {self.name}"

p = Person("Ali")
print(p)  # Person: Ali
Enter fullscreen mode Exit fullscreen mode

4. Operator Overloading

Allows objects to behave like integers, lists, etc.

Example: add 2 bank accounts

class Account:
    def __init__(self, balance):
        self.balance = balance

    def __add__(self, other):
        return Account(self.balance + other.balance)

a1 = Account(500)
a2 = Account(700)

a3 = a1 + a2
print(a3.balance)  # 1200
Enter fullscreen mode Exit fullscreen mode

5. Property Decorator (@property)

Allows you to create getter/setter like in Java but more elegant.

Example

class Product:
    def __init__(self, price):
        self._price = price

    @property
    def price(self):
        return self._price

    @price.setter
    def price(self, value):
        if value >= 0:
            self._price = value
        else:
            raise ValueError("Price can't be negative")
Enter fullscreen mode Exit fullscreen mode

Usage:

p = Product(100)
p.price = 200   # calls setter
print(p.price)  # calls getter
Enter fullscreen mode Exit fullscreen mode

6. Inheritance + MRO (Method Resolution Order)

What MRO means

If a class inherits from multiple parents, Python follows a specific order to find methods.

Example

class A:
    def show(self): print("A")

class B:
    def show(self): print("B")

class C(A, B):
    pass

c = C()
c.show()  # A
print(C.mro())
Enter fullscreen mode Exit fullscreen mode

C.mro() shows:

[C, A, B, object]
Enter fullscreen mode Exit fullscreen mode

7. Abstract Classes (Interfaces in Python)

Used to force child classes to implement certain methods.

Example

from abc import ABC, abstractmethod

class Payment(ABC):
    @abstractmethod
    def pay(self):
        pass

class CardPayment(Payment):
    def pay(self):
        print("Payment via card")
Enter fullscreen mode Exit fullscreen mode

8. Composition (HAS-A relationship)

Instead of inheritance (IS-A), we combine objects.

Real-life

A Car has an Engine.

Example

class Engine:
    def start(self):
        print("Engine starting...")

class Car:
    def __init__(self):
        self.engine = Engine()

    def start(self):
        self.engine.start()

c = Car()
c.start()
Enter fullscreen mode Exit fullscreen mode

9. Duck Typing

Python doesn’t care about the type — only if the object has the required behavior.

Example

class Dog:
    def speak(self): print("Woof")

class Cat:
    def speak(self): print("Meow")

for animal in [Dog(), Cat()]:
    animal.speak()
Enter fullscreen mode Exit fullscreen mode

If it acts like a duck, Python treats it as a duck.


10. Making Objects Callable — __call__

Allows objects to be used like functions.

Example

class Multiply:
    def __init__(self, n):
        self.n = n

    def __call__(self, x):
        return x * self.n

double = Multiply(2)
print(double(10))  # 20
Enter fullscreen mode Exit fullscreen mode

PyTorch uses this heavily for layers & transforms.


11. Metaclasses (Advanced-Advanced)

Metaclasses = classes that create classes.

For example:

class Meta(type):
    def __new__(cls, name, bases, dct):
        print("Creating class:", name)
        return super().__new__(cls, name, bases, dct)

class Test(metaclass=Meta):
    pass
Enter fullscreen mode Exit fullscreen mode

This prints when the class is created.
You rarely need metaclasses until deep framework work.


12. Practical Real-World Example (ML Style)

Here’s how PyTorch builds neural network layers using OOP:

class LinearLayer:
    def __init__(self, input_dim, output_dim):
        self.weights = [[0]*output_dim for _ in range(input_dim)]
        self.bias = [0]*output_dim

    def __call__(self, x):
        # forward pass (simplified)
        return "output vector"
Enter fullscreen mode Exit fullscreen mode

This uses:

  • constructor
  • composition
  • magic method (__call__)

⭐ Mini Exercises (Advanced)

Send your answers and I’ll review.

1. Create a class Rectangle

  • attributes: width, height
  • property: area (read-only using @property)
  • overload + to add two rectangles by area

2. Create a class Temperature

  • stores Celsius
  • provide setter/getter
  • convert to Fahrenheit using a method

3. Create a class Logger

  • keep count of total logs (use @classmethod)
  • method: log(message) → prints message
  • property: total_logs

4. Show an example where composition is better than inheritance.

Top comments (0)