[PEAK] Type and class adaptation
Radek Kanovsky
rk at dat.cz
Sun Nov 21 06:40:56 EST 2004
On Fri, Nov 19, 2004 at 02:15:30PM -0500, Phillip J. Eby wrote:
> On my second reading, I caught a couple of things that I missed before...
>
>
> At 06:21 PM 11/19/04 +0100, Radek Kanovsky wrote:
> >Additionally if I declare
> >adapter for MyClass, this adapter is not applicable to SubClass.
>
> This doesn't sound right; do you have a short code sample I could use to
> test this?
I meant that the only way one can simply define some adapter for user
defined class or type is as follows (fails for int, float, unicode) :
protocols.declareAdapter(
factory = MyClassAsTypeDescriptor,
provides = ITypeDescriptor,
forObjects = [MyClass]
)
I would bet, that it didn't work for subclasses when I have tried it
last time. But it always worked, of course.
> >def dispatch_by_subclass (klass, table):
> > while True:
> > if klass in table:
> > return table[klass]
> > try:
> > klass, = klass.__bases__
>
> This code will raise an AttributeError if it is used on a non-class.
Insufficient testing :-( It worked for few examples with types/classes
arguments. I haven't understood all internals of dispatch package yet.
> > except ValueError:
> > if klass.__bases__:
> > return table.reseed(klass)
> > else:
> > break
> > if klass in table:
> > return table[object]
>
> This last bit is also broken; it's *always* going to return None.
>
> Essentially, the problem with your implementation as far as I can tell, is
> that it doesn't at all consider the possibility that the object is not a
> class. I would recommend that you use 'None' as the key for that
> situation. So, the code would look something like this:
>
> def dispatch_by_subclass (klass, table):
> if isinstance(klass,ClassTypes):
> while True:
> if klass in table:
> return table[klass]
> try:
> klass, = klass.__bases__
> except ValueError:
> if klass.__bases__:
> return table.reseed(klass)
> else:
> break
> if None in table:
> return table[None]
>
> And, the 'ISSubclass.seeds()' method should also include 'None' in its
> seeds.
>
> Essentially, a dispatch function must never return 'None' unless there are
> no cases registered for that situation, and an ITest must create seeds for
> all the possibilities regarding that test. One of the possibilities of a
> subclass test is that the object being tested is not a class, so there
> needs to be a key for that condition. Also, there is the possibility that
> a class is not a subclass of any known test (i.e., it's a new classic
> class). In both of these cases, the 'None' key represents the default
> dispatch path, which is basically a path where none of the subclass-testing
> alternatives are applicable.
>
> This is different from dispatch_by_mro, because in Python everything is an
> *instance* of 'object' eventually, so 'InstanceType' and 'object' are the
> default keys. But, in this case, not everything is a *subclass* of
> 'object', so a different default is needed.
I will try to repair it. Thanks.
Radekk
More information about the PEAK
mailing list