On 2018-03-01 23:38, ooom...@gmail.com wrote:
On Thursday, March 1, 2018 at 12:15:57 AM UTC, Paul Rubin wrote:
RAII is similar to Python's "with" statement.  So it sounds like OP
wants to replace one "malignant carbuncle" with another one.

I would like to understand why you think RAII is not substantially more
pythonic than "With". Below I have sketched out a File-like resource
management scenario using both PEP343 and RAII idioms for comparison.

First lets look at the implementation of the competing resource management
classes:-


class PEP343FileAccess():
     '''
     A File Access-like resource with self-contained Context Manager for use
     with "with".

     This could be acheived with two separate classes but I don't think that
     adds anything except lines of code.
     '''
        
     # Structors
def __init__(self, filename, mode):
         self.filename = filename
         self.mode = mode
         self.handle = None
         # dummy file content accessible only when handle is not None
         self.lines = ['one', 'two', 'three']

     # PEP343 Context Manager compliance
def __enter__(self):
         self.handle = low_level_file_open(self.filename, self.mode) # 
fictitious
         return self
def __exit__(self, extype, exvalue, extraceback):
         low_level_file_close(self.handle) # fictitious function
         self.handle = None
# Example methods

     def __iter__(self):
         assert self.handle, "File has been closed"
         for line in self.lines:
             yield line

     def write(self, line):
         assert self.handle, "File has been closed"
         self.lines.append(line)


class RAIIFileAccess():
     '''File Access-like Resource using RIAA idiom'''
# Structors

     def __init__(self, filename, mode):
         self.handle = low_level_file_open(filename, mode) # fictitious
         # dummy content accessible as long as the object exists (invariant)
         self.lines = ['one', 'two', 'three']
def __del__(self):
         low_level_file_close(self.handle) # fictitious function

     # Example methods

     def __iter__(self):
         for line in self.lines:
             yield line

     def write(self, line):
         self.lines.append(line)


What I see is that PEP343 requires two new methods: __enter__ & __exit__.
RIAA requires no new methods.

RIAA resources are invariant: If you have a reference to it you can use it.

PEP343 resources can not be invariant: To be robust the enter/exit state
must be tracked and checked. (assert self.handle in the example)

Now lets look at example resource usage:-


def pep343_example():

     with PEP343FileAccess("src.txt", 'r') as src,
          PEP343FileAccess("dst.txt", 'w') as dst:

         for line in src:
             dst.write(line)

def raii_example():
src = RAIIFileAccess("src.txt", 'r')
     dst = RAIIFileAccess("dst.txt", 'w')

     for line in src:
         dst.write(line)


PEP343 requires specialised "with" syntax, RIAA requires no new syntax.

Furthermore, although src & dst objects are still accessible outside the
PEP343 "with" block they are not in a usable state (not invariant).

In the RIAA case the resources are guaranteed to be in a usable state as long
as any reference exists (invariant). References can also be safely
passed around.The resource will be freed/closed when the last man has finished
with it, even in the face of exceptions.

What's the difference between 'RAIIFileAccess' and 'open'?
--
https://mail.python.org/mailman/listinfo/python-list

Reply via email to