classical package

Subpackages

Submodules

Module contents

class classical.ArgumentedSubclass(*args, **kwargs)[source]

Bases: classical.descriptors.FactoryProperty

A descriptor that returns an argumented_subclass() of the owner class when accessed.

It allows a class to have attributes that are its own subclasses with additional arguments passed to __init__:

class Tree:
    Peach = ArgumentedSubclass(fruit='peach')
    Pine = ArgumentedSubclass(fruit='cone')
    # both will return subclasses of Tree when accessed

    def __init__(self, fruit):
        self.fruit = fruit

issubclass(Tree.Pine, Tree)  # True
Tree.Pine().fruit  # 'cone'

These properties can be used recursively in combination with each other:

class Polygon:
    Blue = ArgumentedSubclass(color='blue')
    Pentagon = ArgumentedSubclass(sides=5)

    def __init__(self, color=None, sides=3):
        self.color = color
        self.sides = sides

blue_pentagon = Polygon.Pentagon.Blue()
# blue_pentagon.color == 'blue'
# blue_pentagon.sides == 5
class classical.AttributedSubclass(**attributes)[source]

Bases: classical.descriptors.FactoryProperty

A descriptor that returns an attributed_subclass() of the owner class when accessed.

It allows a class to have attributes that are its own subclasses with additional or redefined class attributes:

class Paint:
    solvent = None

    Oil = AttributedSubclass(solvent='turpentine')
    Watercolor = AttributedSubclass(solvent='water')

issubclass(Paint.Oil, Paint)  # True
Paint.Oil.solvent  # 'turpentine'

These properties can be used recursively and in combination with one another.

class classical.AutoProperty(*args, **kwargs)[source]

Bases: classical.descriptors.FactoryProperty

A descriptor that returns an instance of the owner class when accessed.

The instance is created with the custom arguments that are passed to the property’s constructor.

Acts somewhat like an Enum

class Thing:
    book = AutoProperty(color='brown', size=5)
    pencil = AutoProperty(color='green', size=1)
    # both will return instances of Thing when accessed

    def __init__(self, color, size):
        self.color = color
        self.size = size

isinstance(Thing.book, Thing)  # True
Thing.book.color  # 'brown'
Thing.book is Thing.book  # True (the same instance is returned every time)

These properties can be used in a subclass to produce instances of the subclass:

class ClassyThing(Thing):
    pass

isinstance(ClassyThing.book, ClassyThing)  # True

Use AutoProperty(...).terminal to produce instances of the original owner class inside a subclass:

class Thing:
    terminal_thing = AutoProperty().terminal

class ClassyThing(Thing):
    pass

isinstance(ClassyThing.terminal_thing, ClassyThing)  # False
ClassyThing.terminal_thing.__class__  # Thing
class classical.DummySubclass[source]

Bases: classical.descriptors.FactoryProperty

A descriptor that returns a copy of the owner class when accessed (but with a new name equal to the attribute’s name).

class classical.FactoryProperty(factory, *args, **kwargs)[source]

Bases: object

A descriptor that returns an object related to the owner class and created by factory when accessed.

Parameters
  • factory – the object factory. Should have the following signature: factory(cls, name, *args, **kwargs). For example, argumented_subclass() can be used here

  • args – positional arguments for factory

  • kwargs – keyword arguments for factory

FactoryProperty is the base class for:

property terminal: classical.descriptors.FactoryProperty

Return a “terminal” version of the property: if the owner class is subclassed, the object factory will be applied to the original owner of the property instead of the subclass

Consider:

class Thing:
    my_thing = AutoProperty()
    terminal_thing = AutoProperty().terminal

class ClassyThing(Thing):
    pass

isinstance(ClassyThing.my_thing, ClassyThing)  # True
isinstance(ClassyThing.terminal_thing, ClassyThing)  # False

ClassyThing.my_thing.__class__  # ClassyThing
ClassyThing.terminal_thing.__class__  # Thing
classical.argumented_subclass(cls: type, name: str, *args, **kwargs)[source]

Create a subclass of cls identical to the original except for its name and additional arguments passed to __init__

Parameters
  • cls – the class to be subclassed

  • name – name of the new class

  • args – positional arguments for __init__

  • kwargs – keyword arguments for __init__

Returns

a subclass of cls

Say you have

class Square:
    def __init__(self, size, color=None):
        pass  # implementation goes here

The ‘standard’ way to subclass with fixed argument values would be to

class RedSquare1x1(Square):
    def __init__(self):
        super().__init__(1, color='red)

Consider the less-verbose alternative (kind of like the partial function, but for classes):

RedSquare1x1 = argumented_subclass(Square, 'RedSquare1x1', 1, color='red')

Note

Existence of __slots__ (and, consequently, the absence of the instance __dict__) is preserved during subclassing

classical.attributed_subclass(cls: type, name: str, **attributes)[source]

Create a subclass of cls identical to the original, but with additional or redefined attributes

Parameters
  • cls – the class to be subclassed

  • name – name of the new class

  • attributes – new attributes

Returns

a subclass of cls

class Animal:
    pass  # implementation goes here

Bird = attributed_subclass(Animal, 'Bird', wings=2)
pelican = Bird()  # pelican.wings == 2

Note

Existence of __slots__ (and, consequently, the absence of the instance __dict__) is preserved during subclassing