Reputation: 48902
I'm wondering which is the more 'Pythonic' / better way to write methods which process files. Should the method which processes the file close that file as a side effect? Should the concept of the data being a 'file' be completely abstracted from the method which is processing the data, meaning it should expect some 'stream' but not necessarily a file?:
As an example, is it OK to do this:
process(open('somefile','r'))
... carry on
Where process()
closes the file handle:
def process(somefile):
# do some stuff with somefile
somefile.close()
Or is this better:
file = open('somefile','r')
process(file)
file.close()
For what it's worth, I generally am using Python to write relatively simple scripts that are extremely specifically purposed, where I'll likely be the only one ever using them. That said, I don't want to teach myself any bad practices, and I'd rather learn the best way to do things, as even a small job is worth doing well.
Upvotes: 2
Views: 153
Reputation: 7098
Generally, it is better practice for the opener of a file to close the file. In your question, the second example is better.
This is to prevent possible confusion and invalid operations.
Edit: If your real code isn't any more complex than your example code, then it might be better just to have process() open and close the file, since the caller doesn't use the file for anything else. Just pass in the path/name of the file. But if it is conceivable that a caller to process() will use the file before the file should be closed, then leave the file open and close operations outside of process().
Upvotes: 4
Reputation: 2173
No, because it reduces flexibility: if function doesn't close file and caller doesn't need it - caller can close file. If it does but caller still need file open - caller stuck with reopening file, using StringIO, or something else.
Also closing file object require additional assumptions on it's real type (object can support .read() or .write(), but have no meaningful .close()), hindering duck-typing.
And files-left-open is not a problem for CPython - it will be closed on garbage collection instantly after something(open('somefile')). (other implementation will gc and close file too, but at unspecified moment)
Upvotes: 0
Reputation: 798536
Using with
means not having to worry about this.
At least, not on 2.5+.
Upvotes: 4