@classmethod гарантирует, что read_from будет вызван не с экземпляром класса, а с классом@staticmethod гарантирует, что первым параметром не будет self, пользы не много, зато можно подчеркнуть, что данный метод статичен по отношению к экземпляру класса__new__ - создает экземпляр класса, т.е. это конструктор возвращяющий экземпляр, например так:return super().__new__(cls)class ImpossibleIsNothing(metaclass=lambda *args, **kwargs: 42): passПревращает класс в число.
С помощью метаклассов можно сделать любое изменение класса и результат metaclass-а запишется в имя класса.
Метаклассы могут изменять тип словаря в котором хранятся атрибуты класса через метод
__prepare__В отличие от декораторов метаклассы наследуются потомками, т.е. не нужно каждый раз декорировать потомков для реализации задуманного поведения
Metaclasses are deeper magic than 99% of users should ever worry about. If you wonder whether you need them, you don't (the people who actually need them know with certainty that they need them, and don't need an explanation about why).— Тим Питерс
В стандартной библиотеке есть модуль
abc, который с помощью metaclass-ов позволяет писать абстрактные классы в pythonimport abcclass Iterable(metaclass=abc.ABCMeta): @abc.abstractmethod def __iter__(self): passclass Something(Iterable): pass>>> Something()TypeError: Can't instantiate abstract class Something with abstract methods __iter__Модуль
collections.abc содержит абстрактные базовые классы для различных коллекцийНапример, чтобы реализовать словарь запоминающий только последние несколько элементов и чтобы методы
setdefault и аналогичные работали, необходимо его унаследовать от MutableMapping и реализовать методы: __getitem__, __setitem__, __delitem__, __iter__, __len__ABC позволяет удобно проверять реализует ли коллекция необходимый функционал:
from collections import abcissubclass(list, abc.Sequence) # == Trueissubclass({}, abc.Hashable) # == False