我有在Windows中运行的perl脚本。在脚本中我调用另一个perl脚本。我正在尝试将这两个脚本打印到cmd窗口和文件中。这基本上就是我打电话的方式
using IO::Tee
open (my $file, '>>', "C:\\Logs\\logfile.txt") or die "couldn't open log file: $!";
me $tee = IO::Tee->new(\*STDOUT, $file);
# doing some stuff
print $tee "log about what i just did";
# do more stuff
print $tee "more logs";
print $tee `c:\\secondScript.pl arg1`;
print $tee "done with script";
第二个脚本基本上是
# do stuff
print "script 2 log about stuff";
# do more stuff
print "script 2 log about more stuff";
print "script 2 done";
这确实可以获得屏幕和文件的所有内容。但是,在脚本2完成之前,我没有看到“脚本2记录关于东西”,“脚本2记录更多东西”和“脚本2完成”。我想在打印到达后立即看到所有流到屏幕和文件。
答案 0 :(得分:2)
当输出到达终端时,打印到STDOUT通常是行缓冲(以加快速度),否则块缓冲(例如,当将输出重定向到文件时)。
您可以将其视为首先将任何打印的内容放入缓冲区(通常为4096字节大),并且只有当缓冲区已满时(即打印了4096个字符)时,它才会输出到屏幕上。
行缓冲表示仅在找到\n
(或缓冲区已耗尽)后才会在屏幕上显示输出。您的第二个脚本中没有\n
,因此在a)\n
到来之前,b)缓冲区已满,或c)脚本结束时,不会显示输出。
阻止缓冲表示仅在缓冲区已满时显示输出。 \n
这里不会影响这个(除了计算为一个字符)。
为避免缓冲,有一个名为$|
的魔术变量。从docs(向下滚动到$|
部分):
如果设置为非零,则立即强制刷新并在每次写入或之后 在当前选定的输出通道上打印。
因此,您可以将"\n"
附加到您的打印语句中,或者 - 更好 - 在第二个脚本之上设置$| = 1;
(仅限一次,而不是每个print
)。这将减慢第二个脚本的输出(理论上),但对于几行,它将没有任何区别。