Python try again t else finally detailed analysis of execution sequence

Source: Internet
Author: User
Tags try catch

If you are studying python or other programming languages with exception Control, it is very likely that the execution of try catch finally is very simple. If there is an exception, execute retry T, finally is executed regardless of whether there are exceptions. In general, this is the case. However, if more detailed and complex paths are involved and the return Statement is added, it is not that simple.


1. No return Statement


print 'this is a test of code path in try...except...else...finally'print '************************************************************'def exceptTest():    try:        print 'doing some work, and maybe exception will be raised'        raise IndexError('index error')        #print 'after exception raise'        #return 0            except KeyError, e:        print 'in KeyError except'        print e        #return 1    except IndexError, e:        print 'in IndexError except'        print e        #return 2    except ZeroDivisionError, e:        print 'in ZeroDivisionError'        print e        #return 3    else:        print 'no exception'        #return 4    finally:        print 'in finally'        #return 5resultCode = exceptTest()print resultCode

The above code is always used, but the code that is not used for the time being is comment.

If an exception occurs and an exception is caught, finally processes the exception. The output of the above Code is as follows:

this is a test of code path in try...except...else...finally************************************************************doing some work, and maybe exception will be raisedin IndexError exceptindex errorin finallyNone

Then we gradually add a return statement to the above Code to view the code execution result after the return statement is added.


2. Add a return statement


print 'this is a test of code path in try...except...else...finally'print '************************************************************'def exceptTest():    try:        print 'doing some work, and maybe exception will be raised'        raise IndexError('index error')        print 'after exception raise'        return 0            except KeyError, e:        print 'in KeyError except'        print e        return 1    except IndexError, e:        print 'in IndexError except'        print e        return 2    except ZeroDivisionError, e:        print 'in ZeroDivisionError'        print e        return 3    else:        print 'no exception'        return 4    finally:        print 'in finally'        return 5resultCode = exceptTest()print resultCode

At this time, all the branches have a return statement, which causes exceptions. Let's take a look at the output:

this is a test of code path in try...except...else...finally************************************************************doing some work, and maybe exception will be raisedin IndexError exceptindex errorin finally5

After an exception occurs, the raise statement will not be executed again, and then the exception statement will be captured, but the capture exception module has a return. Is it true that the system will not continue to execute the exception statement at this time to directly return the result? However, this is in conflict with the execution of finally statements. We can see that finally statements are actually executed in the result, and the returned value is 5. In finally de, the returned value is.


Then, let's take a look and comment out the finally return value to see what the return value is?

The Code is as follows:

print 'this is a test of code path in try...except...else...finally'print '************************************************************'def exceptTest():    try:        print 'doing some work, and maybe exception will be raised'        raise IndexError('index error')        print 'after exception raise'        return 0            except KeyError, e:        print 'in KeyError except'        print e        return 1    except IndexError, e:        print 'in IndexError except'        print e        return 2    except ZeroDivisionError, e:        print 'in ZeroDivisionError'        print e        return 3    else:        print 'no exception'        return 4    finally:        print 'in finally'        #return 5resultCode = exceptTest()print resultCode

Program output at this time:

this is a test of code path in try...except...else...finally************************************************************doing some work, and maybe exception will be raisedin IndexError exceptindex errorin finally2

The returned value is changed to 2. This is a bit confusing. You don't need to explain the problem first. Let's continue to look at other situations.


3. No exception occurred and the try statement block does not return

The Code is as follows:

print 'this is a test of code path in try...except...else...finally'print '************************************************************'def exceptTest():    try:        print 'doing some work, and maybe exception will be raised'        #raise IndexError('index error')        print 'after exception raise'        #return 0            except KeyError, e:        print 'in KeyError except'        print e        return 1    except IndexError, e:        print 'in IndexError except'        print e        return 2    except ZeroDivisionError, e:        print 'in ZeroDivisionError'        print e        return 3    else:        print 'no exception'        return 4    finally:        print 'in finally'        return 5resultCode = exceptTest()print resultCode

Code output at this time:

this is a test of code path in try...except...else...finally************************************************************doing some work, and maybe exception will be raisedafter exception raiseno exceptionin finally5

Here we verify that if there is no exception, the else statement is executed and the finally statement is executed, and then return 5 of the finally statement.


But what happens when the return statement exists in the try statement block?

4. No exception occurred and the try statement block has a return statement.

print 'this is a test of code path in try...except...else...finally'print '************************************************************'def exceptTest():    try:        print 'doing some work, and maybe exception will be raised'        #raise IndexError('index error')        print 'after exception raise'        return 0            except KeyError, e:        print 'in KeyError except'        print e        return 1    except IndexError, e:        print 'in IndexError except'        print e        return 2    except ZeroDivisionError, e:        print 'in ZeroDivisionError'        print e        return 3    else:        print 'no exception'        return 4    finally:        print 'in finally'        return 5resultCode = exceptTest()print resultCode

Execution result:

this is a test of code path in try...except...else...finally************************************************************doing some work, and maybe exception will be raisedafter exception raisein finally5

Here, else is not executed, which is in conflict with our book knowledge. The finally statement is executed and 5 is returned.

Analysis: because there is no exception, the return Statement in the try block will be executed, but the finally statement must be executed again. Therefore, the finally statement is executed before the return statement in the try. It can be considered that, the finally statement modifies the final returned value, modifies the return value in try to 5, and finally returns the result. Therefore, the else statement is not executed.


5. Exceptions occurred and finally No return Statement


print 'this is a test of code path in try...except...else...finally'print '************************************************************'def exceptTest():    try:        print 'doing some work, and maybe exception will be raised'        raise IndexError('index error')        print 'after exception raise'        return 0            except KeyError, e:        print 'in KeyError except'        print e        return 1    except IndexError, e:        print 'in IndexError except'        print e        return 2    except ZeroDivisionError, e:        print 'in ZeroDivisionError'        print e        return 3    else:        print 'no exception'        return 4    finally:        print 'in finally'        #return 5resultCode = exceptTest()print resultCode

Execution result:

this is a test of code path in try...except...else...finally************************************************************doing some work, and maybe exception will be raisedin IndexError exceptindex errorin finally2

Because an exception occurs, the return Statement in the try cannot be executed, and then executed in the captured commit T. If there is a return statement in commit T, will the return statement be returned directly? The finally statement must be executed. Therefore, the return statement must be put down for the moment and run in finally. Then, after finnaly is executed, it is returned to memory T for execution.


Here, we seem to have found some patterns.

1. if no exception occurs, there is a return statement in try. At this time, the code in the else block cannot be executed, but if there is a return statement in the finally statement, the final return value will be modified, I personally understand that the return statement in try puts the returned value in a CPU register, and then modifies the value of this Register when running the finally statement, finally, return the modified value in the return statement returned to try.

2. if no exception occurs and there is no return statement in try, the code of the else block is executed. However, if there is return in else, the finally code should be executed first, the modification of the returned value is the same as that of the previous one.

3. if an exception occurs, the return Statement in try cannot be executed. If the return statement exists in the commit t statement that captures the exception, you must first execute finally code, the code in finally modifies the final return value, and then returns the final modified return value from the retrun statement in blocks T, which is consistent with the first one.


Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.