问题描述
我想合并两个不同命令的输出(联合),并将它们通过管道传递给单个命令。
一个愚蠢的例子:
我想合并输出的命令:
cat wordlist.txt
ls ~/folder/*
变成:
wc -l
在此示例中,如果wordlist.txt包含5行和3个文件,我希望wc -l
返回8。
$cat wordlist.txt *[magical union thing]* ls ~/folder/* | wc -l
8
我怎么做?
最佳方案
你神奇的结合是分号…和花括号:
{ cat wordlist.txt ; ls ~/folder/* ; } | wc -l
花括号仅将命令分组在一起,因此,管道符号|
会影响组合的输出。
您还可以在命令组周围使用括号()
,这将在子 shell 程序中执行命令。大括号之间有一些细微的差异,例如尝试以下方法:
cd $HOME/Desktop ; (cd $HOME ; pwd) ; pwd
cd $HOME/Desktop ; { cd $HOME ; pwd ; } ; pwd
您会看到,所有环境变量(包括当前工作目录)在退出括号组后都会被重置,而在退出curly-brace组后不会被重置。
至于分号,替代方案包括&&
和||
符号,它们仅在第一个命令成功或失败时才有条件地分别执行第二个命令。
cd $HOME/project && make
ls $HOME/project || echo "Directory not found."
次佳方案
由于wc
接受文件路径作为输入,因此您也可以使用进程替换:
wc -l <(cat wordlist.txt; ls ~/folder/*)
这大致相当于:
echo wordlist.txt > temp
ls ~/folder/* >> temp
wc -l temp
请注意,ls ~/folder/*
还会返回子目录的内容(如果有)(由于全局扩展)。如果只想列出~/folder
的内容,请使用ls ~/folder
。