Usando super () en clases anidadas

Imagina esto:

class A(object): class B(object): def __init__(self): super(B, self).__init__() 

Esto crea un error:

 NameError: el nombre global B no está definido.

He intentado AB , pero luego dice que A no está definido.

Actualizar:

He encontrado el problema.

He tenido una clase como esta:

 class A(object): class B(object): def __init__(self): super(B, self).__init__() someattribute = B() 

En ese ámbito, A aún no está definido.

No estoy seguro de por qué AB no está funcionando correctamente para usted, como debería … Aquí hay algunos resultados de shell que funcionan:

 >>> class A(object): ... class B(object): ... def __init__(self): ... super(AB, self).__init__() ... def getB(self): ... return AB() ... >>> A().getB() <__main__.B object at 0x100496410> 

Como B probablemente nunca se extenderá, esto debería funcionar:

 class A(object): class B(object): def __init__(self): super(self.__class__, self).__init__() 

Si es poco probable que la clase AB participe en alguna herencia múltiple, entonces es mejor que simplemente codifique la llamada del constructor:

 class A(object): class B(object): def __init__(self): object.__init__(self) 

Pero si realmente necesitas tener todo el poder de super, entonces puedes obtener lo que deseas definiendo un descriptor personalizado que inicialice el atributo B perezosamente:

 class LazyAttribute(object): def __init__(self, func, *args, **kwargs): self._func = func self._args = args self._kwargs = kwargs self._value = None def __get__(self, obj, type=None): if self._value is None: print 'created', self._value self._value = self._func(*self._args, **self._kwargs) return self._value class A(object): class B(object): def __init__(self): super(AB, self).__init__() someattribute = LazyAttribute(B) 

Esto hará que el atributo B se cree una instancia la primera vez que se acceda, y luego se reutilizará:

 >>> print A.someattribute created <__main__.B object at 0x00AA8E70> <__main__.B object at 0x00AA8E90> >>> print A().someattribute <__main__.B object at 0x00AA8E90> 

Para obtener más información sobre los descriptores, consulte: http://users.rcn.com/python/download/Descriptor.htm