try:else: w/o except: - why not?

Robin Munn rmunn at pobox.com
Tue Apr 1 01:27:55 EST 2003


yvan <yvan_charpentier at hotmail.com> wrote:
> manus at python.net (Manus Hand) wrote in message news:<1c004553.0303311553.53a9a92b at posting.google.com>...
>> I know that if you want to use else: on a try: block, you need to
>> specify one or more except: clauses.  I guess my question is why
>> this should need to be.
>> 
>> Personally, I have cases where it would be nice to do this:
>> 
>> try:
>>     # some code that may except
>> else:
>>     # but if it didn't except, I want to do this
>> 
>> Instead of writing the code that way, I need to write this:
>> 
>> try:
>>     # some code that may except
>> except:
>>     # and if it does, then, okay, just ignore it
>>     pass
>> else:
>>     # but if it didn't except, I want to do this
>> 
>> I know it's a core language decision and therefore up to Guido,
>> but I am curious (Guido?) if there is something I am missing that
>> would make a simple try:else: construction (without requiring any
>> except: blocks) not make sense?
>> 
>> Manus
> 
> Unless your code throws, execution will resume, so the following
> should behaves as you want.
> 
> try:
>      # some code that may throws
>      # Some code that will be executed if it did not throw above, will
> not if it threw (this is what is in your else block)
> except:
>      # will get there if it threw, will not otherwise

I can see a subtle difference between that block and the OP's "try: ...
else: ..." proposal. For simplicity, I'm going to use single print
statements to represent the code blocks being talked about.

OP's proposal (fragment #1):

    try:
        print "Code that may raise exception"
    else:
        print "No exception was raised"

Your almost-equivalent solution (fragment #2):

    try:
        print "Code that may raise exception"
        print "No exception was raised"
    except:
        print "Oops, caught an exception"

This will have exactly the same behavior as fragment #1 if and only if
the "else:" block can raise no exceptions. If the "else:" block of
fragment #1 is capable of raising exceptions (let's say it writes to a
log file and might raise IOError, for example), then:

Fragment #1 would raise the exception normally.

Fragment #2 would find the exception caught by the "except:" block. This
is fine, but that "except:" block was written with the intent of
catching exceptions from the first print statement, not the second!
Catching IOError, for instance, would be misinterpreted as meaning that
something went wrong with a file in the first block, not the second.

I hope I'm making myself clear. It's late and I'm not having the easiest
time putting my thoughts into words right now.

I find myself opposed to the OP's suggestion, by the way. Explicit is
better than implicit, and adding two lines really does not make that
much difference. I find this:

    try:
        print "Doing stuff"
    except:
        raise
    else:
        print "No exceptions, hooray"

immediately obvious in intent, whereas this:

    try:
        print "Doing stuff"
    else:
        print "No exceptions, hooray"

leaves me with a feeling of "Wait a minute, where's the except: clause?"

-- 
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