Help: except clause ordering

Robin Munn rmunn at pobox.com
Thu Mar 6 15:51:38 EST 2003


Rene Pijlman <reageer.in at de.nieuwsgroep> wrote:
> Bob:
>>C:\Python22\Doc\tut\node11.html#SECTION0011100000000000000000 is the
>>location on my PC with the 9.7.1 Exceptions Can Be Classes section
>>displayed you can see this example which will display
> 
> I tried to access your harddisk, but it failed :-) Let's use
> this:
> http://www.python.org/doc/current/tut/node11.html#SECTION0011710000000000000000
> 
>>class B:
>>    pass
>>class C(B):
>        ^^^^
>>    pass
>>class D(C):
>        ^^^^
>>    pass
> 
>>Why B, B, B rather than D, C, B?
> 
> C inherits from B, and therefore every instance of C is also an
> instance of B.
> 
> Likewise, D inherits from C, and therefore every instance of D
> is also an instance of C, and is also an instance of B.

The reason this is important, by the way, is because of how Python
handles exceptions: when you specify an exception in the "except Foo:"
clause, it will catch not only exception Foo but also any exceptions
that are derived from Foo. So in your example code:

    for c in [B, C, D]:
        try:
            raise c()
        except D:
            print "D"
        except C:
            print "C"
        except B:
            print "B"

When you do "except B:" it will catch all of B, C, and D, since both C
and D are ultimately derived from B. Likewise, "except C:" will catch
both C and D, but not B. So in the order above, you will get the result
"B, C, D" as you expect. But if you flip the order of the expect: lines,
then suddenly the "except B:" test, which will catch all the exceptions,
is at the top and the other lines never get a chance to do their tests.

It's quite possible that the original poster already understood this and
didn't need my explanation; I'm explaining this more for the benefit of
anyone who might stumple across this thread in the archives.

-- 
Robin Munn <rmunn at pobox.com>
http://www.rmunn.com/
PGP key ID: 0x6AFB6838    50FF 2478 CFFB 081A 8338  54F7 845D ACFD 6AFB 6838




More information about the Python-list mailing list