Why use the with statement
Manual file handling risks leaving files open if an error occurs. The with statement is a context manager that calls __exit__ to close the file reliably:
f = open("x.txt") # risky: may never close
try:
...
finally:
f.close()
# is exactly what `with` does for you
Any object implementing __enter__/__exit__ can be used with with.