Skip to main content
ThePythonBook/Assessment

Metaprogramming Assessment

Test your mastery of Python metaprogramming: metaclasses, descriptors, dynamic class creation, and more. These exercises demand a deep understanding of how Python constructs and manipulates classes at runtime.

Progress
900 XP0/10
#1Singleton Metaclass
Write Code

Write a metaclass called SingletonMeta that ensures any class using it as its metaclass can only ever have one instance.

  • Calling the class constructor a second time should return the same object.
  • Define a sample class Database that uses SingletonMeta as its metaclass. Its __init__ should accept a name parameter and store it as self.name.
  • Loading editor...
    #2Typed Validation Descriptor
    Write Code

    Create a descriptor class called TypedField that validates the type of a value on assignment.

  • The constructor accepts a single argument expected_type.
  • On __set__, raise a TypeError with the message "Expected <type_name>" if the value is not an instance of the expected type.
  • Use __set_name__ to store the attribute name.
  • Then define a class Person with:

  • name = TypedField(str)
  • age = TypedField(int)
  • Loading editor...
    #3Fix the Immutable Point
    Fix the Bug

    The code below tries to create an immutable Point by subclassing tuple. However it raises a TypeError at runtime. Fix the bug so that Point(3, 4) works correctly and p.x / p.y return the expected values.

    Do not change the property definitions or remove the tuple base class.

    Loading editor...
    #4Predict Dynamic Attribute Access
    Predict Output

    Read the code carefully and predict exactly what it prints. Pay close attention to when __getattr__ is called versus when it is not.

    Loading editor...
    #5Class Factory with type()
    Write Code

    Write a function make_dataclass(class_name, **fields) that uses type() to dynamically create a class.

  • Each keyword argument is a field name and its default value.
  • The generated class should have an __init__ that accepts those fields as keyword arguments (with the given defaults).
  • The generated class should have a __repr__ that returns ClassName(field1=val1, field2=val2).
  • Example: Dog = make_dataclass("Dog", name="Rex", age=3)

    Loading editor...
    #6Fix the Auto-Repr Decorator
    Fix the Bug

    The auto_repr class decorator is supposed to add a __repr__ method that shows all __init__ parameters. However, it has a bug: it always prints the class name as "cls" instead of the real class name.

    Fix the decorator so the repr uses the actual class name.

    Loading editor...
    #7Predict Metaclass Creation Order
    Predict Output

    Read the code carefully and predict exactly what it prints. Focus on the order in which the metaclass methods execute.

    Loading editor...
    #8Refactor with __slots__
    Refactor

    The Sensor class below works but uses a regular instance dict. Refactor it to use __slots__ for memory efficiency.

    Requirements:

  • Add __slots__ with the correct attribute names.
  • The class must still work exactly the same way.
  • After refactoring, instances should not have a __dict__.
  • Loading editor...
    #9Fix __setattr__ Recursion
    Fix the Bug

    The Logged class overrides __setattr__ to record attribute changes in a log list. However, it causes infinite recursion. Fix the bug while keeping the logging behavior.

    The log should collect strings in the format "set <name> = <value>". The log attribute itself should not be logged.

    Loading editor...
    #10Refactor to Abstract Base Class
    Refactor

    The code below uses a base class Shape with methods that raise NotImplementedError. Refactor it to use Python's abc module so that:

  • Shape is an abstract base class.
  • area() and perimeter() are abstract methods.
  • Attempting to instantiate Shape directly raises TypeError.
  • The Circle subclass should remain functional.
  • Loading editor...