The role of Python __enter__ and __exit__, and its relationship with the WITH statement

Source: Internet
Author: User
Tags file handling integer division stack trace

What is the WITH statement?

There are some tasks that may need to be set up beforehand to do cleanup work afterwards. For this scenario, Python's with statement provides a very convenient way to handle it. A good example is file handling, where you need to get a file handle, read the data from the file, and then close the file handle.

If you do not use the WITH statement, the code is as follows:

File = open ("/tmp/foo.txt"= file.read () file.close ()

Here are two questions. One is the possibility of forgetting to close the file handle, and the other is that the file read data is abnormal and no processing is done. The following is an enhanced version of handling exceptions:

File = open ("/tmp/foo.txt")try:    = file.read () finally :    file.close ()

Although this code works well, it's too verbose. This is the time for a show with a skill. In addition to having a more elegant syntax, with can also handle the exception generated by the context environment very well. The following is the code with the version:

With open ("/tmp/foo.txt") as file:    = File.read ()

How does the with work?

It looks magical, but not just magic, and Python's handling of with is smart. The basic idea is that the object with which the value is evaluated must have a __enter__() method, a __exit__() method.

After the statement that follows with is evaluated, the method that returns the object is __enter__() called, and the return value of the method is assigned to the variable following the AS. When the code block after the with is all executed, the method that previously returned the object is called __exit__() .

The following example can specify how with works:

#!/usr/bin/env python#with_example01.pyclassSample:def __enter__(self):Print "In __enter__ ()"        return "Foo"    def __exit__(self, type, value, trace):Print "In __exit__ ()"defget_sample ():returnSample () with Get_sample () as Sample:Print "Sample:", sample output is as follows Bash-3.2$./With_example01.pyin__enter__() Sample:fooin__exit__()

As you can see,

__enter__()Method is executed
__enter__()The value returned by the method-this example is "Foo", assigned to the variable ' sample '
Execute code block, print variable "sample" with the value "Foo"
__exit__()Method is called

With the real power of it is that it can handle exceptions. You may have noticed that the method of the sample class __exit__ has three parameters Val,type and trace. These parameters are quite useful in exception handling. Let's change the code to see how it works.

#!/usr/bin/env python#with_example02.pyclassSample:def __enter__(self):return Selfdef __exit__(self, type, value, trace):Print "Type:", typePrint "Value:", ValuePrint "Trace:", Tracedefdo_something (self): bar= 1/0returnBar + 10With Sample () as sample:sample.do_something ()

In this example, the Get_sample () behind with is changed to sample (). This does not matter, as long as the object that follows with the statement returned is the same as the __enter__() __exit__() method. In this example, the method of sample () __enter__() returns the newly created sample object and assigns a value to the variable sample.

After the code executes:

bash-3.2$./With_example02.pytype:<type'exceptions. Zerodivisionerror'>Value:integer Divisionormodulo by Zerotrace:<traceback Object at 0x1004a8128>Traceback (most recent): File"./with_example02.py", line 19,inch<module>Sample.do_somet hing () File"./with_example02.py", line 15,inchdo_something Bar= 1/0zerodivisionerror:integer DivisionorModulo by zero

In fact, the method is executed when any exception is thrown in the code block following the with __exit__() . As the example shows, when an exception is thrown, the associated type,value and stack trace are passed __exit__() to the method, so the thrown Zerodivisionerror exception is printed out. When you develop a library, clean up resources, close files, and so on, all in a __exit__ way.

As a result, Python's with statement provides an effective mechanism for making the code more concise and for easier cleanup when the exception is generated.

The role of Python __enter__ and __exit__, and its relationship with the WITH statement

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.