metaclasses
Samuele Pedroni
pedronis at bluewin.ch
Thu Feb 27 07:16:54 EST 2003
>
> So, object <class '__main__.Sub'> cannot be deleted because of
> this reference to it. Exactly where this tuple comes from is
> an interesting puzzle (I think it's object keeping track of all
> of its subclasses, but that's just a guess),
yes, but it politely uses weakrefs, see below
> but in practice I
> do think it means no class object is ever truly deleted...
>
no, I have modifed slightly the code:
import sys
class MyMetaclass(type):
def __init__(cls, name, bases, dict):
super(MyMetaclass, cls).__init__(name, bases, dict)
print 'initialized', cls.__name__
def __del__(cls):
print 'deleted', cls.__name__
class MyClass(object):
if len(sys.argv)>1 and sys.argv[1]=='meta':
__metaclass__ = MyMetaclass
pass
class Sub(MyClass):
pass
del Sub
import gc,pprint
gc.collect() # force involved weak-refs to be cleared
print "MyClass subclasses",MyClass.__subclasses__()
print "garbage",gc.garbage
def isActuallySub(x):
return type(x) is MyMetaclass and x is not MyClass
a = [x for x in gc.get_objects() if isActuallySub(x)]
del x
if not a:
print "Sub not held"
else:
referrers = [x for x in gc.get_referrers(a[0]) if x is not a]
print len(referrers),'still holding on to Sub...:'
pprint.pprint(referrers)
Now:
C:\exp\py-subclasses-gc>\transit\Py23\python test.py
MyClass subclasses []
garbage []
Sub not held
here all is good.
C:\exp\py-subclasses-gc>\transit\Py23\python test.py meta
initialized MyClass
initialized Sub
MyClass subclasses [<class '__main__.Sub'>]
garbage [<class '__main__.Sub'>]
4 still holding on to Sub...:
[[<class '__main__.Sub'>],
(<class '__main__.Sub'>, <class '__main__.MyClass'>, <type 'object'>),
<attribute '__dict__' of 'Sub' objects>,
<attribute '__weakref__' of 'Sub' objects>]
so we have a cycle involving __del__s ??? Sub and MyMetaclass form a cycle
but it be breaked by weak-refs??? this merits further study...
More information about the Python-list
mailing list