Las metaclases son clases que generan otras clases. Es una herramienta eficiente para la verificación de clases, para evitar que las subclases hereden ciertas funciones de clase y la generación dinámica de clases. Aquí discutiremos cómo crear una instancia de una metaclase que se ejecute tanto en Python 2 como en Python 3. Antes de profundizar en esto, repasemos el diseño del código para cada versión de Python.
Python 3
En Python 3, se crea una instancia de una metaclase mientras se declara una clase, proporcionando la Metaclase al argumento de palabra clave de la metaclase. Veamos la forma preferida de hacer esto en Python 3.
Python3
class MetaCls(type): def __new__(cls, name, bases, attrs): return super(MetaCls, cls).__new__(cls, name, bases, attrs) class C(object, metaclass=MetaCls): pass print('Type of class C:',type(C))
Type of class C: <class '__main__.MetaCls'>
Aquí, hemos creado una clase llamada C proporcionando la clase MetaCls al argumento de la palabra clave metaclase . Puede ver el tipo de clase C como MetaCls.
Nota: MetaCls es una metaclase que se heredó directamente de type .
Python 2
Ahora, veamos cómo crear una instancia de una metaclase en Python 2. En Python 3, hemos visto que la metaclase se menciona en el argumento de la palabra clave durante la declaración de la clase; mientras que en Python 2, una metaclase se asigna en el cuerpo de la clase usando un atributo __metaclass__. Veamos el código a continuación:
Python
class MetaCls(type): def __new__(cls, name, bases, attrs): return super(MetaCls, cls).__new__(cls, name, bases, attrs) class C(object): __metaclass__ = MetaCls print(type(C))
<class '__main__.MetaCls'>
Código de metaclase que se ejecuta tanto en Python 2 como en Python 3
Ahora está claro cómo difiere la sintaxis en Python 2 y Python 3. Esta diferencia en la sintaxis puede crear problemas si intenta migrar su código de Python 2 a Python 3. Dado que Python 3 es incompatible con versiones anteriores, la sintaxis de Python 3 no se ejecuta en Python 2 y viceversa.
Aquí viene la importancia de una herramienta llamada seis . Proporciona dos formas de declarar una metaclase que garantiza la compatibilidad cruzada.
- Mediante la creación de una clase suplente
- como decorador
En el primer método, crearemos una clase suplente y la usaremos como una subclase directa. Veamos el siguiente código.
Python3
import six class MetaCls(type): def __new__(cls, name, bases, attrs): return super(MetaCls, cls).__new__(cls, name, bases, attrs) class C(six.with_metaclass(MetaCls)): pass print(type(C))
<class '__main__.Meta'>
Ahora, veamos cómo crear una instancia de metaclase usando un decorador.
Python3
import six class MetaCls(type): def __new__(cls, name, bases, attrs): return super(MetaCls, cls).__new__(cls, name, bases, attrs) @six.add_metaclass(MetaCls) class C(object): pass print(type(C))
<class '__main__.MetaCls'>
Publicación traducida automáticamente
Artículo escrito por SonuGeorge y traducido por Barcelona Geeks. The original can be accessed here. Licence: CCBY-SA