Shell / Bash Command获得STDOUT的第n行

有没有任何bash命令可以让你获得STDOUT的第n行?

也就是说,有些事情会采取这一点

$ ls -l -rw-r--r--@ 1 root wheel my.txt -rw-r--r--@ 1 root wheel files.txt -rw-r--r--@ 1 root wheel here.txt 

并做类似的事情

 $ ls -l | magic-command 2 -rw-r--r--@ 1 root wheel files.txt 

我意识到在编写脚本的时候这是不好的做法,但是当我每天使用shell时,能够以这种方式过滤我的STDOUT是非常有用的。

我也意识到这将是半平凡的写命令(缓冲区STDOUT,返回一个特定的行),但我想知道是否有一些标准的 shell命令来做到这一点,将没有我放下脚本到位可用。

使用sed ,只是为了变化:

 ls -l | sed -n 2p 

使用这种替代方法,由于在打印所需的行时停止读取input,看起来效率更高,可能会在送入过程中生成SIGPIPE,从而可能会生成不需要的错误消息:

 ls -l | sed -n -e '2{p;q}' 

我经常看到,我通常使用第一个(反正更容易input),虽然ls不是在SIGPIPE时发出抱怨的命令。

对于一系列的线路:

 ls -l | sed -n 2,4p 

对于几个线的范围:

 ls -l | sed -n -e 2,4p -e 20,30p ls -l | sed -n -e '2,4p;20,30p' 
 ls -l | head -2 | tail -1 

替代良好的头/尾方式:

 ls -al | awk 'NR==2' 

要么

 ls -al | sed -n '2p' 

从sed1line :

 # print line number 52 sed -n '52p' # method 1 sed '52!d' # method 2 sed '52q;d' # method 3, efficient on large files 

从awk1line :

 # print line number 52 awk 'NR==52' awk 'NR==52 {print;exit}' # more efficient on large files 

试试这个sed版本:

 ls -l | sed '2 ! d' 

它说“删除所有不是第二个的行”。

为了完整性;-)

较短的代码

 find / | awk NR==3 

寿命更短

 find / | awk 'NR==3 {print $0; exit}' 

你可以使用awk:

 ls -l | awk 'NR==2' 

更新

上面的代码不会因为错误而得到我们想要的: ls -l命令的第一行是总行 。 为此,以下修改的代码将起作用:

 ls -l | awk 'NR==3' 

Perl很容易提供给你?

 $ perl -n -e 'if ($. == 7) { print; exit(0); }' 

显然可以用你想要的数字replace7。

另一个海报build议

 ls -l | head -2 | tail -1 

但是如果你把头伸进尾巴,看起来直到N线的东西都会被处理两次。

pipe尾成头

 ls -l | tail -n +2 | head -n1 

会更有效率吗?

是的,最有效的方式(Jonathan Leffler已经指出)是使用sed打印和退出:

 set -o pipefail # cf. help set time -p ls -l | sed -n -e '2{p;q;}' # only print the second line & quit (on Mac OS X) echo "$?: ${PIPESTATUS[*]}" # cf. man bash | less -p 'PIPESTATUS' 

sed没有在我的情况下工作。 我提议:

对于“奇数”行1,3,5,7 … ls | awk'0 ==(NR + 1)%2'

对于“偶数”行2,4,6,8 ls | awk'0 ==(NR)%2'

为了更完整..

 ls -l | (for ((x=0;x<2;x++)) ; do read ; done ; head -n1) 

抛开线条,直到第二条线,然后打印出第一条线。 所以,它打印第三行。

如果只是第二行

 ls -l | (read; head -n1) 

把尽可能多的阅读必要。

我在.bash_profile中添加了这个

 function gdf(){ DELETE_FILE_PATH=$(git log --diff-filter=D --summary | grep delete | grep $1 | awk '{print $4}') SHA=$(git log --all -- $DELETE_FILE_PATH | grep commit | head -n 1 | awk '{print $2}') git show $SHA -- $DELETE_FILE_PATH } 

这是有用的

 gdf <file name>