连续处理 tail -f 输出

连续处理 tail -f 输出

我有一个文件,其中连续附加数字:

1
2
3
4

我想计算它们的平均值,也是连续的,即:

1
1.5
2
2,5

我不想定期检查文件,我想以 tail -f 工作的方式进行检查 - 一旦添加一行,我就会执行平均计算。

是否可以?

更新型多巴胺问题已移至https://stackoverflow.com/questions/9400306/countinuous-processing-of-tail-f-output

答案1

是的。管道tail -f连接到处理平均值的脚本。管道永远不会关闭,脚本可以立即处理收到的每一行...它会阻塞直到出现一行。

另外,大家应该记住,可以计算移动平均值而不必每次都添加所有值。我已经见过足够多的例子了,我觉得有必要提一下。

#generator.pl
$| = 1; #immediate flush
while (1) {
    print int rand(100), "\n";
    sleep 1;
}

#average.pl
$| = 1; #immediate output flush
my $average = 0;
my $count = 0;
while (<>) {
    $average = ($average * $count + $_) / ($count + 1);
    $count++;
    print $average, "\n";
}

$ perl generator.pl > source &
[2] 15564
(reverse-i-search)`': ^C
$ tail -f source | perl average.pl
54
28
27.6666666666667
35
41

并且,只是为了开个玩笑:

$tail -f source | awk '{total+=$0; count+=1; print total/count}'

这也具有即时反馈。在我看来,您的问题是由正在写入 tail 正在读取的文件的应用程序缓冲引起的。

http://www.pixelbeat.org/programming/stdio_buffering/了解相关信息。

答案2

这是一个使用 dc 的简单解决方案。

tail -f | dc -e '5k 0 d sc st [? lc 1 + sc lt + st lt lc / p c lax] sa lax'

我不确定 dc 是否支持尾递归,如果不支持,该程序将会泄漏内存。dc 的文档真的很糟糕。:)

怎么,你不喜欢脑力劳动?:)

这是一个 Ruby 中的简单解决方案。 tail -f | ruby -e 'sum=total=0.0; while line=gets; total += line.to_f; sum += 1; puts total/sum; end'

相关内容