Is there a way to open a file for both reading and writing?
As a workaround, I open the file for writing, close it, then open it again for reading. But is there a way to open a file for both reading and writing?
mmap
mmap
is a great idea, but what if you have to deal with concurrency? Is there a way to reserve access?
Here's how you read a file, and then write to it (overwriting any existing data), without closing and reopening:
with open(filename, "r+") as f:
data = f.read()
f.seek(0)
f.write(output)
f.truncate()
Summarize the I/O behaviors
Mode r r+ w w+ a a+ Read + + + + Write + + + + + Create + + + + Cover + + Point in the beginning + + + + Point in the end + +
and the decision branch
https://i.stack.imgur.com/t4k06.png
r+
is the canonical mode for reading and writing at the same time. This is not different from using the fopen()
system call since file()
/ open()
is just a tiny wrapper around this operating system call.
open
is a system call, fopen
is not a system call. It's fopen
that's a wrapper around open
.
I have tried something like this and it works as expected:
f = open("c:\\log.log", 'r+b')
f.write("\x5F\x9D\x3E")
f.read(100)
f.close()
Where:
f.read(size) - To read a file’s contents, call f.read(size), which reads some quantity of data and returns it as a string.
And:
f.write(string) writes the contents of string to the file, returning None.
Also if you open Python tutorial about reading and writing files you will find that:
'r+' opens the file for both reading and writing. On Windows, 'b' appended to the mode opens the file in binary mode, so there are also modes like 'rb', 'wb', and 'r+b'.
truncate
method to stop this.
Success story sharing
a+
to cover end-case that the file does not exist (will be created)a
states 'on some Unix systems, means that all writes append to the end of the file regardless of the current seek position'. In this case thef.seek(0)
won't work as expected. I just fell foul of this on Linux.seek
andtruncate
is used here. Most of the readers come from google and do copy-paste.seek(0)
does: it places the fp to position0
(i.e. the beginning).truncate()
truncate the file to the provided number of bytes, i.e. removes all of the file content after the specified number of bytes. Imagine that your file has the stringHello, world
and you writeBye
. If you don'ttruncate()
the content at the end will beByelo, world
, since you never deleted the text that existed in the file.truncate()
truncates the file to the current fp.