查看文件开始和结束的Bash方法


8

在基于队列的集群上,从命令(例如)显示待处理作业的队列showqueue

该命令以列的形式返回诸如名称等合理数据的列表,但是列/数据对于该问题并不重要。

我喜欢使用的工具watch一样watch showqueue,有时(有一个别名alias watch="watch ",以力别名扩展我的命令来观看)。前几行有有价值的数据(正在运行的作业),然后是挂起的作业等,最后还有一些有价值的摘要。

但是,有时showqueue的输出不在屏幕上(我知道这真是难以置信)!理想情况下,我希望可以通过某种方式同时查看文件的开头和结尾。

到目前为止showqueue > file; head -n 20 file > file2; echo "..." >> file2 ; tail -n 20 file >> file2; cat file2,我最好的是:,并使用watch其别名。

有谁知道更灵活或更实用的东西?我的解决方案使用bash循环有点麻烦,可以使“ ...”中断多行显示,根本无法适应调整终端窗口的大小,而且我敢肯定,我还错过了更多东西。

有什么建议么?


作为重复项关闭,但问题仅是相似的(我的问题更多是关于一个命令,我了解到的,而不是文件),并且此处没有显示答案,但是如果您坚持,则必须这样做
MadisonCooper

2
很公平。我已经重新营业了。请注意,您接受的答案仅适用于大型输出,如我在Command的答案中指出的那样,以显示文件的前几行和后几​​行seq 30 | (head && tail)例如,尝试)。
斯特凡Chazelas

2
我的意思是那个答案。这Q&A有我的两个答案,因为另一个Q&A与它(见合并问题的历史
斯特凡Chazelas

Answers:


14

您是否要执行以下操作?同时显示头和尾的输出。

$ showqueue | (head && tail)

6
的某些实现head可能读取多于10行,并且没有任何内容可供tail读取。该实用程序不应该这样做,我相信GNU工具在这方面表现良好。也可以使用head; echo '...'; tail来获得点。
库萨兰达

是的,再加上@Kusalananda的评论,它比我的解决方案简洁得多。我现在将其标记为正确!谢谢。
MadisonCooper

4
@Kusalananda,不,在我的系统上,GNU头(coreutils 8.26)读取8192字节的块。它确实会尝试找回,但显然不会发生。无论如何,是否真的需要head不过度阅读?(在Mac上相同,似乎可以按块阅读)
ilkkachu

2
@ilkkachu是的,即使站在足够长的输出上,它的尾巴部分有时还是空白的(我知道,因为我使用的是head -n 35,并且已经满了),但是幸运的是,这只是观看时的方便,我可以等待3必要时刷新几秒钟。
MadisonCooper

3
@ Kusalananda,POSIX允许实现在无法查找输入且大多数实现都可以实现的情况下执行此操作。不这样做将意味着一次读取一个字节,这将非常低效(或者将数据放回到受支持的管道上,这会导致各种不同的问题)。只有head我知道,在同一时间,以避免读取过去的10换行符读取一个字节的实现是ksh93的的head内置。
斯特凡Chazelas

2

使用与您相同的方法,使用一个临时文件,但执行时间略短一些:

showqueue >/tmp/q.out; head -n 20 /tmp/q.out; echo '...'; tail -n 20 /tmp/q.out

这不会从作为讨论的相同问题的影响下,另一种答案,但可能表现出同样的行两次,如果输出短于40行。


+1我想到的是相同的解决方案,只是略有不同,使用tee来使输出直接进入,head而仅将保存的输出用于tail

2

awk解决方案从头和尾显示任意数量的行(更改n=3以设置数量):

$ seq 99999 | awk -v n=3 'NR <= n; NR > n { a[NR] = $0; delete a[NR-n]; } 
     END { print "..."; for (i = NR-n+1; i <= NR; i++) if (i in a) print a[i]; }'
1
2
3
...
99997
99998
99999

撰写本文时,即使输入的内容比线条短,头部和尾部也不会重叠2*n

在某些awk实现中,for (x in a) print a[x];在该END部分中使用也可以。但是总的来说,不能保证以正确的顺序返回数组条目,例如,不能以mawk返回。


如果m是文件中的行数,并且是m < 2n,则将打印2n - m空行。也请看这里 ;-)。仅在GNU awkfor (x in a)中顺序迭代; 如果您认为它也适用,请使用> 10个值进行测试。mawk
mosvy

@mosvy,哦,糟糕,我忘了在意识到x in a不正确之后再次检查。立即修复,谢谢。Stéphane链接到的问题中还有一个awk答案。不过,我喜欢模数技巧!
ilkkachu

0

您可以使用简单的awk脚本。在n = 3处添加了最后3行的圆形缓冲区

awk 'NR<=n {print $0} { A[NR%n]=$0 } END { for (i=1; i<=n; ++i) if (NR+i>2*n)print A[(NR+i)%n] }' n=3 < <( seq 10 )

更新之后,它变得不那么简单了,


1
这只会显示第一行和最后一行。要显示更多信息,您必须更改NR==1NR <= 10(或其他内容),然后将行收集到(圆形?)缓冲区中,然后在END块中输出。
库萨兰达

是的,让我更新
Abdurrahim

当行数少于2 * n时,这将打印两次行。
mosvy

:)好吧,现在补充一下,我很好奇您接下来会发现什么:D
Abdurrahim
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.