我想使用像 tail 这样的程序来跟踪正在写入的文件,但不显示最新的行。
例如,当关注一个新文件时,如果文件少于 30 行,则不会显示任何文本。当文件写入超过 30 行后,将从第 1 行开始写入屏幕。
因此,当第 31-40 行写入文件时,第 1-10 行也将写入屏幕。
如果没有简单的方法可以用 tail 做到这一点,也许有一种方法可以在每次第一个文件扩展一行时将第一个文件的前一行写入新文件,而新文件的 tail...
答案1
与 @muru 相同,但使用模运算符而不是存储和删除:
tail -fn+1 some/file | awk -v n=30 '
NR > n {print s[NR % n]}
{s[NR % n] = $0}
END{for (i = NR - n + 1; i <= NR; i++) print s[i % n]}'
答案2
也许用 awk 缓冲:
tail -n +0 -f some/file | awk '{b[NR] = $0} NR > 30 {print b[NR-30]; delete b[NR-30]} END {for (i = NR - 29; i <= NR; i++) print b[i]}'
awk 代码,扩展:
{
b[NR] = $0 # save the current line in a buffer array
}
NR > 30 { # once we have more than 30 lines
print b[NR-30]; # print the line from 30 lines ago
delete b[NR-30]; # and delete it
}
END { # once the pipe closes, print the rest
for (i = NR - 29; i <= NR; i++)
print b[i]
}
答案3
这不是很有效,因为它会在上次读取文件后两秒重新读取文件,如果输出太快,您将错过行,但否则会完成这项工作:
watch 'tail -n40 /path/to/file | head -n10'
答案4
这取决于您跟踪文件的方式,但我认为您可以通过以下方式最简单地做到这一点:
tail -n0 -F path/to/my/file.log
当您运行上述代码时,如果进程将行附加到文件末尾(例如,./run_process.sh >> file.log
),您将仅获得最新添加的行,就像大多数应用程序记录文件一样。