无法将持续运行的Python脚本输出写入指定日志文件的问题
解决Python脚本重定向输出后日志文件为空的问题
你的脚本遇到了标准输出缓冲区未及时刷新的典型问题,这是Python将stdout重定向到文件时很容易踩的坑,我来帮你分析并解决:
问题根源
当你把sys.stdout重定向到文件时,Python默认会切换为全缓冲模式——输出内容会先暂存在内存缓冲区里,只有当缓冲区被填满、程序正常结束,或者手动触发刷新操作时,才会真正写入磁盘文件。如果你的脚本一直卡在while(True)循环里(比如LAN连接还没建立),缓冲区的内容就会一直留在内存中,导致你看到的日志文件始终是空的。另外,你的脚本没有处理文件关闭的逻辑,要是脚本意外中断,缓冲区里的内容也会直接丢失。
修复方案(任选一种即可)
方案1:给print语句添加自动刷新参数
最简单的修改方式,直接在每个print里开启flush=True,强制每次输出都立即写入文件:
import subprocess import time import os import sys sys.stdout = open('/home/pi/Desktop/file.txt', 'w') print('checking LAN connections...', flush=True) time.sleep(2) while(True): # 用with语句自动关闭文件,避免资源泄漏 with open("/sys/class/net/eth0/carrier","r") as f: state = f.read() if('1' in state): print('LAN connection to target device established successfully !', flush=True) break else: print('Please establish LAN connection to the target device !', flush=True) time.sleep(4) # 脚本结束前手动关闭文件,确保内容写入 sys.stdout.close()
方案2:打开日志文件时启用行缓冲
在打开日志文件时指定buffering=1,开启行缓冲模式,这样每次输出换行时都会自动把内容写入文件:
import subprocess import time import os import sys # 设置buffering=1启用行缓冲 sys.stdout = open('/home/pi/Desktop/file.txt', 'w', buffering=1) print('checking LAN connections...') time.sleep(2) while(True): with open("/sys/class/net/eth0/carrier","r") as f: state = f.read() if('1' in state): print('LAN connection to target device established successfully !') break else: print('Please establish LAN connection to the target device !') time.sleep(4) sys.stdout.close()
方案3:用with语句管理文件(更安全)
使用with语句可以自动处理文件的关闭操作,哪怕脚本中途出错,也能保证缓冲区的内容写入磁盘:
import subprocess import time import os import sys # with块结束后会自动关闭文件,无需手动调用close() with open('/home/pi/Desktop/file.txt', 'w', buffering=1) as log_file: sys.stdout = log_file print('checking LAN connections...') time.sleep(2) while(True): with open("/sys/class/net/eth0/carrier","r") as f: state = f.read() if('1' in state): print('LAN connection to target device established successfully !') break else: print('Please establish LAN connection to the target device !') time.sleep(4)
额外优化建议
- 读取
/sys/class/net/eth0/carrier时用with语句,能自动关闭文件,避免不必要的资源占用。 - 如果脚本可能长期运行,建议添加超时逻辑,避免陷入无限循环。
内容的提问来源于stack exchange,提问作者Hbib
相关产品推荐
相关产品推荐

