On 01/05/2007 18.09, Phillip J. Eby wrote: >> The alternative is to code the automatic finalization steps using >> weakref callbacks. For those used to using __del__, it takes a little >> while to learn the idiom but essentially the technique is hold a proxy >> or ref with a callback to a boundmethod for finalization: >> self.resource = resource = CreateResource() >> self.callbacks.append(proxy(resource, resource.closedown)) >> In this manner, all of the object's resources can be freed automatically >> when the object is collected. Note, that the callbacks only bind >> the resource object and not client object, so the client object >> can already have been collected and the teardown code can be run >> without risk of resurrecting the client (with a possibly invalid state). > > I'm a bit confused about the above. My understanding is that in order for > a weakref's callback to be invoked, the weakref itself *must still be > live*. That means that if 'self' in your example above is collected, then > the weakref no longer exists, so the closedown won't be called.
Yes, but as far as I understand it, the GC does special care to ensure that the callback of a weakref that is *not* part of a cyclic trash being collected is always called. See this comment in gcmodule.c: * OTOH, if wr isn't part of CT, we should invoke the callback: the * weakref outlived the trash. Note that since wr isn't CT in this * case, its callback can't be CT either -- wr acted as an external * root to this generation, and therefore its callback did too. So * nothing in CT is reachable from the callback either, so it's hard * to imagine how calling it later could create a problem for us. wr * is moved to wrcb_to_call in this case. I might be wrong about the inners of GC, but I have used the weakref idiom many times and it always appeared to be working. > In principle I'm in favor of ditching __del__, as long as there's actually > a viable technique for doing so. My own experience has been that setting > up a simple mechanism to replace it (and that actually works) is really > difficult, because you have to find some place for the weakref itself to > live, which usually means a global dictionary or something of that > sort. Others suggested that such a framework could be prepared, but I have not seen one yet. It would be nice if the gc or weakref modules grew a facility to > make it easier to register finalization callbacks, and could optionally > check whether you were registering a callback that referenced the thing you > were tying the callback's life to. That'd be absolutely great! OTOH, the GC could possibly re-verify such assertion every time it kicks in (when a special debug flag is activated). -- Giovanni Bajo Develer S.r.l. http://www.develer.com _______________________________________________ Python-3000 mailing list Python-3000@python.org http://mail.python.org/mailman/listinfo/python-3000 Unsubscribe: http://mail.python.org/mailman/options/python-3000/archive%40mail-archive.com