Metaclasse
![Abbozzo](http://upload.wikimedia.org/wikipedia/commons/thumb/0/0e/Puzzle_stub.svg/45px-Puzzle_stub.svg.png)
In programmazione a oggetti, una metaclasse è una classe le cui istanze sono a loro volta classi. Questo concetto è strettamente legato al concetto di riflessione (reflection), che si applica a quegli strumenti concettuali che permettono di rappresentare, all'interno di un programma, informazioni sulle parti costituenti del programma stesso (tipicamente classi e oggetti).
Il concetto di metaclasse è impiegato soprattutto a livello teorico (appare, per esempio, nella definizione formale della semantica dello Unified Modeling Language), ma trova anche applicazioni dirette in diversi linguaggi di programmazione. In Java, per esempio, tutte le classi sono concettualmente considerate istanze dell'unica metaclasse Class
, in Python type
è una metaclasse.
Python
In Python una metaclasse è per lo più definita come una sottoclasse di type.
class AttributeInitType(type): def __call__(self, *args, **kwargs): """ Create a new instance. """ # First, create the object in the normal default way. obj = type.__call__(self, *args) # Additionally, set attributes on the new object. for name, value in kwargs.items(): setattr(obj, name, value) # Return the new object. return obj
Questa metaclasse sovrascrive solamente la creazione dell'oggetto. Tutti gli altri aspetti della classe e comportamento dell'oggetto sono ancora gestiti da type. Ora la classe Car può essere riscritta per usare questa metaclasse. In Python 2 si fa assegnando __metaclass__ nella definizione di classe mentre in Python 3 fornendo all'argomento della classe metaclass = M)
class Car(object): __metaclass__ = AttributeInitType __slots__ = ['make', 'model', 'year', 'color'] @property def description(self): """ Return a description of this car. """ return "%s %s %s %s" % (self.color, self.year, self.make, self.model)
Gli oggetti Car
si possono istanziare così:
cars = [ Car(make='Toyota', model='Prius', year=2005, color='green'), Car(make='Ford', model='Prefect', year=1979, color='blue')]
Un altro esempio di Metaclasse in Python:
class Spell(type): def __new__(cls,classname,super,classdict): def pph( hours ): return lambda self : self.pay_per_hour * hours classdict['pay_per_hour'] = 12 classdict['day_salary'] = pph(8) classdict['week_salary'] = pph(8*5) classdict['year_salary'] = pph(8*5*4*12) classdict['month_salary'] = pph(8*5*4) return type.__new__(cls, classname, super, classdict ) class Person(metaclass=Spell): def __init__(self,name,lastname,bday): self.name = name self.lastname = lastname self.bday = bday def get_name(self): return self._name def get_lastname(self): return self._lastname def get_bday(self): return self._bday def __repr__(self): return "name: {0}, lastname: {1}, bday: {2}".format(self.name,self.lastname,self.bday) if __name__ == "__main__": persona = Person("Mario","Rossi","23 novembre 65")
Linguaggi che supportano le metaclassi
- Common Lisp, attraverso CLOS
- Delphi e altre versioni di Object Pascal influenzate da esso
- Groovy
- Objective-C
- Python
- Perl, attraverso la metaclasse pragma, come anche utilizzando Moose
- Ruby
- Smalltalk
Voci correlate
- Metamodellazione
- Riflessione (informatica)