Python Contextlib context Manager

Source: Internet
Author: User

1. With operator

Reading and writing files in Python may require code like this

try-finally Read and write files

File_text = Nonetry:    = open ('./text'R  ')    print  file_text.read ()except  IOError, ex:    Traceback.print_exc () finally :     if file_text:        file_text.close ()

Similarly, using a thread lock in Python may require code like this

Try-finally Thread Lock

Lock = Threading. Lock () Lock.acquire ()try:    passexcept  Exception, ex:    Traceback.print_exc ()finally:    lock.release ()

You might find this very inconvenient, and Python provides the with operator, which you can do

With read and write files

With open ('./text'r') as File_text:     Print file_text.read ()

With Thread lock

With Lock:     Pass

is not much more convenient.

In fact, not only lock and file can use the with operator.

In fact, any object, as long as context management is implemented correctly, can use the WITH statement. Implementation of context management is achieved through both __enter__ and __exit__ methods.

2. Context Management

Context management can mask the complexity of the context for us. For example, we implement a class cat that implements its __enter__ and __exit__ methods.

__enter__ (self): This method is called when the context manager is entered, and its return value is placed in the variable specified by the as specifier in the With-as statement.

__exit__ (SELF,TYPE,VALUE,TB): This method is called from the context manager. If there is an exception, type, value, and TB are the exception types, values, and trace information, respectively. If there is no exception,

Each of the 3 parameters is set to none. This method returns a value of TRUE or FALSE, indicating whether the thrown exception was received or not processed. If False is returned, the thrown exception is passed out of context.

As follows.

classCat (object):def __init__(self, name): Self.name=namedef __enter__(self):Print 'enter from Cat named%s'%Self.namereturn SelfdefHello (self):Print 'Hello,%s'%Self.namedef __exit__(self, exc_type, Exc_val, EXC_TB):Print 'exit from Cat named%s'%Self.name

Execute, and print the results

With Cat ('Tom') as Tom:     from from cat named Tom

Here we execute as Tom obtains an instance of the Cat class, which is obtained by the return of the __enter__ method.

Of course, we can manage multiple, please note the order of entry and exit.

With Cat ('Tom') as Tom, Cat ('Harry') as Harry:    Tom.hello ()    fromand from Cat named Tom

3, ContextManager

Maybe you still find it troublesome to realize __enter__ and __exit__. Python provides the Contextlib.contextmanager

Let's rewrite the example above, using ContextManager

 from Import ContextManager as _contextmanager@_contextmanager def Cat (name):     Print ' Enter cat named%s ' % name    yield  name    print'exit cat Named%s' % name

Execute, and print the results

With Cat ('kitty') as Kitty:    print'Hello,%s  ' % kittyenter cat named Kittyhello, Kittyexit cat named Kitty

The instance after as is returned by the yield statement. Here is the return of a string.

Of course, managing multiple instances is also supported

With Cat ('kitty') as Kitty, Cat ('Tom') as Tom:     Print ' Hello,%s ' % kitty    print'Hello,%s' % tomenter Cat named Kittyenter cat named Tomhello, Kittyhello, Tomexit cat named Tomexit cat named Kitty

4, finally give an example

Implementing Redis distributed locks using the online text manager

ImportRedisImport TimeImportThreadingImportTraceback fromContextlibImportContextManager as _contextmanagerr= Redis. Redis (host='localhost', port=6379, db=0) @_contextmanagerdefdist_lock (client, key): Dist_lock_key='lock:%s'%KeyTry: _acquire_lock (client, Dist_lock_key)yield_release_lock (client, Dist_lock_key)exceptException, ex:Passdef_acquire_lock (client, key): Is_lock= R.set (key, 1, Nx=true, ex=10)    if  notIs_lock:RaiseException ("already locked!")def_release_lock (client, key): Client.delete (key)deffunc (): while1:        Try: With Dist_lock (R,"Key"):                Print "*"Time.sleep (8)        exceptException, ex:Passthread_list=list () forIinchRange (10): Thread_list.append (Threading. Thread (Target=func)) forThreadinchThread_list:thread.start () forThreadinchThread_list:thread.join ()

Python Contextlib context Manager

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.