[Frederic Rentsch] > Working with read and write operations on a file I stumbled on a > complication when writes fail following a read to the end. > > >>> f = file ('T:/z', 'r+b') > >>> f.write ('abcdefg') > >>> f.tell () > 30L > >>> f.seek (0) > >>> f.read () > 'abcdefg' > >>> f.flush () # Calling or not makes no difference > >>> f.write ('abcdefg')
Nothing is defined about what happens at this point, and this is inherited from C. In standard C, if you want to read following a write, or write following a read, on the same stream, you must perform a file-positioning operation (typically a seek) between them. > Traceback (most recent call last): > File "<pyshell#62>", line 1, in -toplevel- > f.write ('abcdefg') > IOError: (0, 'Error') That's one possible result. Since nothing is defined, any other outcome is also a possible result ;-) > Flushing doesn't help. Right, and because flush() is not a file-positioning operation. > I found two work arounds: > > >>> f.read () > 'abcdefg' > >>> f.read () # Workaround 1: A second read (returning an empty string) > '' > >>> f.write ('abcdefg') > (No error) Purely an accident; may or may not "work" the next time you try it, or on another platform; etc. > >>> f.read () > 'abcdefg' > >>> f.seek (f.tell ()) # Workaround 2: Setting the cursor (to where it is!) That's a correct approach. f.seek(0, 1) (seek 0 bytes from the current position) is a little easier to spell. > >>> f.write ('abcdefg') > (No error) > > I found no problem with writing into the file. So it looks like it has > to do with the cursor which a read puts past the end, unless it is past > the end, in which case it goes back to the end. Is there a less kludgy > alternative to "fseek (ftell ())"? As above, you need to seek when switching from reading to writing, or from writing to reading. -- http://mail.python.org/mailman/listinfo/python-list