背景

背景

背景

我正在运行一个显示多个主机上进程的命令。下面是命令:

execAll -m "$HOSTS" 'hostname; ps -ef | grep build | grep -v grep; ipcs | grep 666'

试图

我现在想将ipcs | grep 666命令的一部分通过管道传输到awk '{print $2}',然后通过管道传输到kill -9以终止所有活动进程。以下是我尝试过的:

execAll -m "$HOSTS" 'hostname; ps -ef | grep build | grep -v grep; ipcs | grep 666 | awk '{print $2}' | xargs kill -9'

但是,awk需要单引号来运行其参数,并且上面的命令也需要单引号。我得到的错误是Missing }.,我将其归因于上面的引用问题。

问题

在上述情况下如何成功运行awk并杀死进程?

答案1

但是,awk需要单引号来运行其参数,[...]

并不真地。引号只是一个 shell 构造,它们告诉 shell 不要展开美元符号并将字符串保持为一个片段,而不是在空格上将其打断。 awk 看到的只是字符串{print $2},它不知道它是如何生成的。您可以使用双引号和反斜杠转义达到相同的效果。所有这些都应该是相同的:

awk '{print $2}'
awk "{print \$2}"
awk {print\ \$2}

后两者可以毫无问题地放入单引号字符串中。

或者,如果您的 shell 是 Bash 或其他支持 ANSI C 引用的 shell,$'..'则可以将外部引号更改为$'..',然后也用反斜杠转义单引号:

echo $'do or don\'t'

顾名思义,其他 C 风格转义符(例如\n, \t, \", \', \\)也可以在其中工作$'..'

答案2

awk 本身并不“需要”单引号。您只需要确保脚本主体包含您希望它包含的内容。如果您转义以下内容,则会找到双引号$

execAll ... '...; ipcs | awk "/666/ {print \$2}" | xargs ...'

相关内容