Customizing Sizes and Sorting via len, eq, lt

🏷️ Object-Oriented Programming (OOP) Basics / Special Dunder Methods

When working with custom objects in Python, you often need them to behave like built-in types. For example, you might want to check how many items are in a custom collection, compare two objects for equality, or sort a list of objects. This is where special dunder methods come inβ€”they let you define how your objects respond to Python's built-in functions and operators.


βš™οΈ What Are Dunder Methods?

Dunder methods (short for "double underscore") are special methods that Python looks for when you use certain operations. They allow your custom objects to integrate seamlessly with Python's syntax and built-in functions.

  • len: Called when you use the len() function on your object
  • eq: Called when you use the == operator to compare two objects
  • lt: Called when you use the < operator to compare two objects

These three methods together enable two powerful features: determining the size of your object and enabling sorting behavior.


πŸ“Š Using len to Define Object Size

The len method should return an integer representing the "size" or "length" of your object. This is commonly used for custom collection-like classes.

Consider a simple TaskList class that holds a collection of tasks:

  • Define a class TaskList with an internal list to store tasks
  • Implement len to return the number of tasks in the list
  • When you call len(task_list), Python automatically invokes your len method

Example implementation:

  • class TaskList: with an init method that creates self.tasks = []
  • def len(self): returns len(self.tasks)
  • After adding three tasks, len(task_list) returns 3

This makes your custom object behave just like a list or dictionary when checking its size.


πŸ› οΈ Using eq for Equality Comparison

The eq method defines what it means for two objects to be equal. Without it, Python compares objects by their memory address, meaning two objects with identical data would be considered different.

When implementing eq:

  • Accept two parameters: self and other (the object to compare against)
  • Return True if the objects should be considered equal, False otherwise
  • Always check if other is an instance of the same class to avoid errors

Example for a Server class:

  • class Server: with attributes like hostname and ip_address
  • def eq(self, other): checks if isinstance(other, Server) and then compares self.hostname == other.hostname
  • Two server objects with the same hostname are now considered equal

This is especially useful when you need to check for duplicate objects or compare configurations.


πŸ•΅οΈ Using lt for Sorting and Ordering

The lt method (less than) is the key to making your objects sortable. Python's sorting algorithms use this method to determine the order of items.

When implementing lt:

  • Accept two parameters: self and other
  • Return True if self should come before other in sorted order
  • Return False otherwise
  • Include proper error handling for incompatible types

Example for a Process class:

  • class Process: with attributes like priority and name
  • def lt(self, other): returns self.priority < other.priority
  • When you call sorted(list_of_processes), Python uses lt to determine the order

You can also combine eq and lt to create a complete ordering system.


πŸ“‹ Comparison Table: Dunder Methods for Sizes and Sorting

Method Triggered By Purpose Return Value
len len(object) Returns the size or count Integer
eq object1 == object2 Checks if objects are equal Boolean
lt object1 < object2 Determines sorting order Boolean

πŸ”„ Putting It All Together: A Complete Example

Here is how you might combine all three methods in a single class:

Class: Document

  • Attributes: title, word_count, author
  • len: Returns the word_count value
  • eq: Two documents are equal if they have the same title and author
  • lt: Documents are sorted by word_count (smaller first)

When you create a list of Document objects:

  • len(doc) gives you the word count
  • doc1 == doc2 checks if they have the same title and author
  • sorted(documents) arranges them from shortest to longest

This makes your custom objects feel like native Python types.


⚑ Best Practices for Engineers

  • Always implement eq when you implement lt to maintain consistency
  • Use isinstance() checks in eq and lt to handle comparisons with different types gracefully
  • For complex sorting, consider implementing gt (greater than) as well, though lt alone is sufficient for sorting
  • Remember that len should return a non-negative integer; returning 0 means the object is empty
  • When sorting objects, Python's sorted() function and list.sort() method both rely on lt by default

🎯 Key Takeaways

  • len customizes what len() returns for your objects
  • eq defines equality logic for the == operator
  • lt enables sorting by defining the "less than" relationship
  • These methods make your custom objects work seamlessly with Python's built-in functions and operators
  • Implementing these dunder methods is essential for creating intuitive, Pythonic classes that engineers can use without learning special APIs

By mastering these three dunder methods, you give your custom objects the same capabilities as Python's built-in types, making your code more readable and your objects more powerful.


These dunder methods let engineers define how objects report their size and how they compare with each other for sorting.


πŸ”§ Example 1: Using len to return a custom size

This example shows how to make an object respond to the len() function with a custom value.

class Backpack:
    def __init__(self, items):
        self.items = items

    def __len__(self):
        return len(self.items)

my_bag = Backpack(["laptop", "notebook", "pen"])
print(len(my_bag))

πŸ“€ Output: 3


πŸ”§ Example 2: Using eq to compare objects by value

This example shows how to make two objects equal when their internal data matches.

class Book:
    def __init__(self, title, pages):
        self.title = title
        self.pages = pages

    def __eq__(self, other):
        return self.pages == other.pages

book_a = Book("Python 101", 300)
book_b = Book("Data Science", 300)
book_c = Book("Web Dev", 200)
print(book_a == book_b)
print(book_a == book_c)

πŸ“€ Output: True
πŸ“€ Output: False


πŸ”§ Example 3: Using lt to enable sorting by a custom field

This example shows how to make objects sortable by one of their attributes.

class Employee:
    def __init__(self, name, salary):
        self.name = name
        self.salary = salary

    def __lt__(self, other):
        return self.salary < other.salary

    def __repr__(self):
        return f"{self.name}: ${self.salary}"

emp1 = Employee("Alice", 75000)
emp2 = Employee("Bob", 60000)
emp3 = Employee("Carol", 90000)
employees = [emp1, emp2, emp3]
employees.sort()
print(employees)

πŸ“€ Output: [Bob: $60000, Alice: $75000, Carol: $90000]


πŸ”§ Example 4: Combining len, eq, and lt in one class

This example shows how all three methods work together in a single class for full size and sorting control.

class Warehouse:
    def __init__(self, name, items):
        self.name = name
        self.items = items

    def __len__(self):
        return len(self.items)

    def __eq__(self, other):
        return len(self) == len(other)

    def __lt__(self, other):
        return len(self) < len(other)

    def __repr__(self):
        return f"{self.name} ({len(self)} items)"

wh_a = Warehouse("East", ["boxes", "tools"])
wh_b = Warehouse("West", ["boxes", "tools", "machines"])
wh_c = Warehouse("North", ["boxes", "tools"])
print(len(wh_a))
print(wh_a == wh_c)
print(wh_a < wh_b)
warehouses = [wh_b, wh_a, wh_c]
warehouses.sort()
print(warehouses)

πŸ“€ Output: 2
πŸ“€ Output: True
πŸ“€ Output: True
πŸ“€ Output: [East (2 items), North (2 items), West (3 items)]


πŸ”§ Example 5: Practical sorting of custom objects by multiple criteria

This example shows how engineers can sort a list of custom objects using lt with tie-breaking logic.

class Student:
    def __init__(self, name, grade, age):
        self.name = name
        self.grade = grade
        self.age = age

    def __lt__(self, other):
        if self.grade != other.grade:
            return self.grade > other.grade
        return self.age < other.age

    def __repr__(self):
        return f"{self.name} (Grade: {self.grade}, Age: {self.age})"

s1 = Student("Zara", 85, 22)
s2 = Student("Mike", 92, 21)
s3 = Student("Lena", 85, 20)
s4 = Student("Omar", 92, 23)
students = [s1, s2, s3, s4]
students.sort()
print(students)

πŸ“€ Output: [Mike (Grade: 92, Age: 21), Omar (Grade: 92, Age: 23), Lena (Grade: 85, Age: 20), Zara (Grade: 85, Age: 22)]


πŸ“Š Quick Comparison Table

Method Purpose Example Use
__len__ Returns size when len(obj) is called Count items in a collection
__eq__ Defines equality between two objects Compare objects by value
__lt__ Defines "less than" for sorting Sort objects by a custom field

When working with custom objects in Python, you often need them to behave like built-in types. For example, you might want to check how many items are in a custom collection, compare two objects for equality, or sort a list of objects. This is where special dunder methods come inβ€”they let you define how your objects respond to Python's built-in functions and operators.


βš™οΈ What Are Dunder Methods?

Dunder methods (short for "double underscore") are special methods that Python looks for when you use certain operations. They allow your custom objects to integrate seamlessly with Python's syntax and built-in functions.

  • len: Called when you use the len() function on your object
  • eq: Called when you use the == operator to compare two objects
  • lt: Called when you use the < operator to compare two objects

These three methods together enable two powerful features: determining the size of your object and enabling sorting behavior.


πŸ“Š Using len to Define Object Size

The len method should return an integer representing the "size" or "length" of your object. This is commonly used for custom collection-like classes.

Consider a simple TaskList class that holds a collection of tasks:

  • Define a class TaskList with an internal list to store tasks
  • Implement len to return the number of tasks in the list
  • When you call len(task_list), Python automatically invokes your len method

Example implementation:

  • class TaskList: with an init method that creates self.tasks = []
  • def len(self): returns len(self.tasks)
  • After adding three tasks, len(task_list) returns 3

This makes your custom object behave just like a list or dictionary when checking its size.


πŸ› οΈ Using eq for Equality Comparison

The eq method defines what it means for two objects to be equal. Without it, Python compares objects by their memory address, meaning two objects with identical data would be considered different.

When implementing eq:

  • Accept two parameters: self and other (the object to compare against)
  • Return True if the objects should be considered equal, False otherwise
  • Always check if other is an instance of the same class to avoid errors

Example for a Server class:

  • class Server: with attributes like hostname and ip_address
  • def eq(self, other): checks if isinstance(other, Server) and then compares self.hostname == other.hostname
  • Two server objects with the same hostname are now considered equal

This is especially useful when you need to check for duplicate objects or compare configurations.


πŸ•΅οΈ Using lt for Sorting and Ordering

The lt method (less than) is the key to making your objects sortable. Python's sorting algorithms use this method to determine the order of items.

When implementing lt:

  • Accept two parameters: self and other
  • Return True if self should come before other in sorted order
  • Return False otherwise
  • Include proper error handling for incompatible types

Example for a Process class:

  • class Process: with attributes like priority and name
  • def lt(self, other): returns self.priority < other.priority
  • When you call sorted(list_of_processes), Python uses lt to determine the order

You can also combine eq and lt to create a complete ordering system.


πŸ“‹ Comparison Table: Dunder Methods for Sizes and Sorting

Method Triggered By Purpose Return Value
len len(object) Returns the size or count Integer
eq object1 == object2 Checks if objects are equal Boolean
lt object1 < object2 Determines sorting order Boolean

πŸ”„ Putting It All Together: A Complete Example

Here is how you might combine all three methods in a single class:

Class: Document

  • Attributes: title, word_count, author
  • len: Returns the word_count value
  • eq: Two documents are equal if they have the same title and author
  • lt: Documents are sorted by word_count (smaller first)

When you create a list of Document objects:

  • len(doc) gives you the word count
  • doc1 == doc2 checks if they have the same title and author
  • sorted(documents) arranges them from shortest to longest

This makes your custom objects feel like native Python types.


⚑ Best Practices for Engineers

  • Always implement eq when you implement lt to maintain consistency
  • Use isinstance() checks in eq and lt to handle comparisons with different types gracefully
  • For complex sorting, consider implementing gt (greater than) as well, though lt alone is sufficient for sorting
  • Remember that len should return a non-negative integer; returning 0 means the object is empty
  • When sorting objects, Python's sorted() function and list.sort() method both rely on lt by default

🎯 Key Takeaways

  • len customizes what len() returns for your objects
  • eq defines equality logic for the == operator
  • lt enables sorting by defining the "less than" relationship
  • These methods make your custom objects work seamlessly with Python's built-in functions and operators
  • Implementing these dunder methods is essential for creating intuitive, Pythonic classes that engineers can use without learning special APIs

By mastering these three dunder methods, you give your custom objects the same capabilities as Python's built-in types, making your code more readable and your objects more powerful.

Interactive Views

You are currently in πŸ“š All-in-One mode. Use the tabs at the top to switch to πŸ“– Theory Only or πŸ’» Code Only views.

These dunder methods let engineers define how objects report their size and how they compare with each other for sorting.


πŸ”§ Example 1: Using len to return a custom size

This example shows how to make an object respond to the len() function with a custom value.

class Backpack:
    def __init__(self, items):
        self.items = items

    def __len__(self):
        return len(self.items)

my_bag = Backpack(["laptop", "notebook", "pen"])
print(len(my_bag))

πŸ“€ Output: 3


πŸ”§ Example 2: Using eq to compare objects by value

This example shows how to make two objects equal when their internal data matches.

class Book:
    def __init__(self, title, pages):
        self.title = title
        self.pages = pages

    def __eq__(self, other):
        return self.pages == other.pages

book_a = Book("Python 101", 300)
book_b = Book("Data Science", 300)
book_c = Book("Web Dev", 200)
print(book_a == book_b)
print(book_a == book_c)

πŸ“€ Output: True
πŸ“€ Output: False


πŸ”§ Example 3: Using lt to enable sorting by a custom field

This example shows how to make objects sortable by one of their attributes.

class Employee:
    def __init__(self, name, salary):
        self.name = name
        self.salary = salary

    def __lt__(self, other):
        return self.salary < other.salary

    def __repr__(self):
        return f"{self.name}: ${self.salary}"

emp1 = Employee("Alice", 75000)
emp2 = Employee("Bob", 60000)
emp3 = Employee("Carol", 90000)
employees = [emp1, emp2, emp3]
employees.sort()
print(employees)

πŸ“€ Output: [Bob: $60000, Alice: $75000, Carol: $90000]


πŸ”§ Example 4: Combining len, eq, and lt in one class

This example shows how all three methods work together in a single class for full size and sorting control.

class Warehouse:
    def __init__(self, name, items):
        self.name = name
        self.items = items

    def __len__(self):
        return len(self.items)

    def __eq__(self, other):
        return len(self) == len(other)

    def __lt__(self, other):
        return len(self) < len(other)

    def __repr__(self):
        return f"{self.name} ({len(self)} items)"

wh_a = Warehouse("East", ["boxes", "tools"])
wh_b = Warehouse("West", ["boxes", "tools", "machines"])
wh_c = Warehouse("North", ["boxes", "tools"])
print(len(wh_a))
print(wh_a == wh_c)
print(wh_a < wh_b)
warehouses = [wh_b, wh_a, wh_c]
warehouses.sort()
print(warehouses)

πŸ“€ Output: 2
πŸ“€ Output: True
πŸ“€ Output: True
πŸ“€ Output: [East (2 items), North (2 items), West (3 items)]


πŸ”§ Example 5: Practical sorting of custom objects by multiple criteria

This example shows how engineers can sort a list of custom objects using lt with tie-breaking logic.

class Student:
    def __init__(self, name, grade, age):
        self.name = name
        self.grade = grade
        self.age = age

    def __lt__(self, other):
        if self.grade != other.grade:
            return self.grade > other.grade
        return self.age < other.age

    def __repr__(self):
        return f"{self.name} (Grade: {self.grade}, Age: {self.age})"

s1 = Student("Zara", 85, 22)
s2 = Student("Mike", 92, 21)
s3 = Student("Lena", 85, 20)
s4 = Student("Omar", 92, 23)
students = [s1, s2, s3, s4]
students.sort()
print(students)

πŸ“€ Output: [Mike (Grade: 92, Age: 21), Omar (Grade: 92, Age: 23), Lena (Grade: 85, Age: 20), Zara (Grade: 85, Age: 22)]


πŸ“Š Quick Comparison Table

Method Purpose Example Use
__len__ Returns size when len(obj) is called Count items in a collection
__eq__ Defines equality between two objects Compare objects by value
__lt__ Defines "less than" for sorting Sort objects by a custom field