Python 使用pynotify读取新行
我正在尝试显示添加到文件中的新行。 假设我有一个Python 使用pynotify读取新行,python,file,events,pynotify,Python,File,Events,Pynotify,我正在尝试显示添加到文件中的新行。 假设我有一个示例文件.txt: 1. line 1 2. line 2 3. line 3 我想检查此文件是否有新行,然后显示该行(无需再次打印所有文件) 我的想法是在while循环之前的某个地方读取所有行,然后打印下一行,但是我的代码中有错误,它会在循环之后立即检查f.next()。我将解决两个问题: 如何在文件上实现tail 以及如何使用pyinotify模块 尾随文件 在代码中,您需要: 尝试使用read或readlines尽可能多地阅读全
示例文件.txt
:
1. line 1
2. line 2
3. line 3
我想检查此文件是否有新行,然后显示该行(无需再次打印所有文件)
我的想法是在while循环之前的某个地方读取所有行,然后打印下一行,但是我的代码中有错误,它会在循环之后立即检查
f.next()
。我将解决两个问题:
- 如何在文件上实现
tail
- 以及如何使用
模块pyinotify
- 尝试使用
或read
尽可能多地阅读全文readlines
- 将文件倒带到最后一行的开头,直到可以使用
打印seek
f = open(PATH)
for line in f.readlines():
print line[:-1]
while True:
time.sleep(5)
try:
line_start = f.tell()
new_lines = f.read()
last_n = new_lines.rfind('\n')
if last_n >= 0:
# We got at least one full line
line_start += last_n + 1
print new_lines[:last_n]
else:
# No complete line yet
print 'no line'
f.seek(line_start)
except KeyboardInterrupt:
notifier.stop()
break
您可以在此处找到更多示例,尽管有些示例没有说明文件中不以换行符结尾的添加内容:
pyinotify
的事件处理程序中,如文档中所述
check_events
返回True
如果有要处理的事件,但它实际上并不处理这些事件,因此它本身将始终返回True
,直到事件处理完毕
另外,在睡眠时尽量避免
/循环。Inotify增加了在不影响资源的情况下,在收到事件后立即处理事件的功能。while
/睡眠
循环的反应性较低
下面是在pyinotify
上形成的前两种方法
1.无休无止的监控
如果没有其他事件循环,这是首选方法,因为它将是最具反应性的:
PATH = os.path.join(os.path.expanduser('~/'), 'experiments', 'testfile')
class EventHandler(pyinotify.ProcessEvent):
def __init__(self, *args, **kwargs):
super(EventHandler, self).__init__(*args, **kwargs)
self.file = open(PATH)
self.position = 0
self.print_lines()
def process_IN_MODIFY(self, event):
print 'event received'
self.print_lines()
def print_lines(self):
new_lines = self.file.read()
last_n = new_lines.rfind('\n')
if last_n >= 0:
self.position += last_n + 1
print new_lines[:last_n]
else:
print 'no line'
self.file.seek(self.position)
wm = pyinotify.WatchManager()
handler = EventHandler()
notifier = pyinotify.Notifier(wm, handler)
wm.add_watch(PATH, pyinotify.IN_MODIFY, rec=True)
notifier.loop()
2.定期监测
如果您已经有了一个处理循环,那么只需定期调用process\u events
。EventHandler
类与方法1中的相同,但是现在我们不再调用notifier.loop()
而是向通知程序添加一个小的超时,并实现我们自己的事件循环
...
wm = pyinotify.WatchManager()
handler = EventHandler()
notifier = pyinotify.Notifier(wm, handler, timeout=10)
wm.add_watch(PATH, pyinotify.IN_MODIFY, rec=True)
while True:
# Do something unrelated to pyinotify
time.sleep(5)
notifier.process_events()
#loop in case more events appear while we are processing
while notifier.check_events():
notifier.read_events()
notifier.process_events()
这太棒了!非常感谢!我想知道如何防止new\u lines=self.file.read()
。read()
似乎非常昂贵,因为每次编辑文件时,您都必须读取整个文件,这是不明智的。@zizheng wuself.file.read()
将从当前文件描述符位置读取,该位置由self.file.seek(self.position)
设置。因为我们只在最后一次看到“\n”之后搜索回该位置,所以这将只读取新行,而不是整个文件。在数据写入时没有终止'\n'到文件的(罕见)事件中,可以通过存储读取的数据而不是返回到最后的'\n'来进一步避免某些读取。
...
wm = pyinotify.WatchManager()
handler = EventHandler()
notifier = pyinotify.Notifier(wm, handler, timeout=10)
wm.add_watch(PATH, pyinotify.IN_MODIFY, rec=True)
while True:
# Do something unrelated to pyinotify
time.sleep(5)
notifier.process_events()
#loop in case more events appear while we are processing
while notifier.check_events():
notifier.read_events()
notifier.process_events()