打开已打开的文件不会引发异常



考虑这两个python程序:

script_a.py:

from datetime import datetime
from time import sleep
while True:
    sleep(1)
    with open('foo.txt', 'w') as f:
        sleep(3)
        s = str(datetime.now())
        f.write(s)
        sleep(3)

script_b.py:

while True:
    with open('foo.txt') as f:
        s = f.read()
        print s

执行命令script_a.py。当它正在运行时,启动script_b.py。两者都将愉快地运行,但如果script_a.py当前打开文件,script_b.py输出一个空字符串。

我期待一个IOError异常被提出,告诉我文件已经打开,但它没有发生,而是文件看起来是空的。为什么会这样,检查它是否被另一个进程打开的正确方法是什么?简单地检查是否返回一个空字符串,然后再次尝试,直到读取到其他内容,或者有更python的方法吗?

查看其他关于在Python中如何打开多个文件的答案和注释。如果您已经阅读了所有这些内容,并且仍然希望在POSIX平台上锁定对文件的访问权限,那么您可以使用fcntl库。

请记住:A)其他程序可能会忽略您对文件的锁定,B)一些网络文件系统没有很好地实现锁定,或者根本没有实现锁定C)确保非常小心地释放锁并避免死锁,因为flock不会检测到它[1][2]。

例子…script_a.py

from datetime import datetime
from time import sleep
import fcntl
while True:
    sleep(1)
    with open('foo.txt', 'w') as f:
        s = str(datetime.now())
        print datetime.now(), "Waiting for lock"
        fcntl.flock(f, fcntl.LOCK_EX)
        print datetime.now(), "Lock clear, writing"
        sleep(3)
        f.write(s)
        print datetime.now(), "releasing lock"
        fcntl.flock(f, fcntl.LOCK_UN)

script_b.py

import fcntl
from datetime import datetime
while True:
    with open('foo.txt') as f:
        print datetime.now(), "Getting lock"
        fcntl.flock(f, fcntl.LOCK_EX)
        print datetime.now(), "Got lock, reading file"
        s = f.read()
        print datetime.now(), "Read file, releasing lock"
        fcntl.flock(f, fcntl.LOCK_UN)
        print s

希望这对你有帮助!

你可以随意打开一个文件,只要操作系统不阻止你。这对于在一个文件中获取多个游标以进行复杂操作有时很有用。

script_b.py认为文件为空的原因是文件为空:

with open('foo.txt', 'w') as f:

w模式打开文件会立即擦除(即截断)文件。在script_a中,最初有3秒的间隙,其中文件完全是100%空的,这就是script_b所看到的。

在调用f.write后的下一个三秒间隙中,文件仍然是…可能是空的。这是由于缓冲——磁盘上的文件不能保证包含你用write写入的所有内容,直到你使用close(即退出上下文管理器块)或在文件句柄上手动调用flush

或者,您可以在非缓冲模式下打开,这样写入总是立即写入磁盘。

with open('foo.txt','w',0) as f:
   #no buffering, f.write() writes immediately to disk

相关内容

  • 没有找到相关文章

最新更新