変数に格納されているコマンドを実行しようとしています。
cmd="grep -i \"word1\" filename | grep -i \"word2\""
eval $cmd
しかし、スクリプトを実行するとエラーが発生します。
grep: |: No such file or directory
grep: grep: No such file or directory
このエラーは発生せず、例のようなコマンドをどのように実行できますか?
答え1
引用符で囲む必要があり、二重引用符を"$cmd"
使用しないことをお勧めします"
。とにかくこれを実行するには必須ですeval
。これは、.shell変数が単一の単純コマンドの制限を超えて拡張されないため、|pipe
複合コマンドを実行しようとします。
だから:
cmd='grep -i "word1" filename | grep -i "word2"'
eval "$cmd"
引用符なしで拡張すると、ファイル名の生成や問題が$cmd
発生する可能性があります。$IFS
確実に参照されていることを確認してください。また、コンテンツに"word[12]"
二重引用符やバックスラッシュなどが含まれていないことを確認してください。それ以外の場合は、引用スタイルを再評価する必要があります。
さて、エラーを詳しく見ると、エラーが何であるかを正確に知ることができます。
grep: |: No such file or directory
grep: grep: No such file or directory
その場合は、次のようにしてください。
echo | echo
最初は2番目にewlineをecho
印刷します。私がするなら:\n
echo
stdin
set \| echo
echo "$@"
まず、パイプと。echo
各引数を印刷します。|
echo
違いは、|
最初のケースのパイプがシェルのパーサーによってトークンとして解釈され、トークンとして解釈されることです。 2番目のケースでは、|
シェルがパイプトークンを検索しながら、$
拡張トークンも検索します。したがって、パイプがその値に置き換えられていない|
ため、検索されませんでした。"$@"
その場合は、次のようにしてください。
grep -i "word" filename \| grep -i "word2"
|
...コマンドは分離されていませんが、対応する引数がgrep
あるため、同じ結果が得られます。内部ファイル場所。
$cmd
デフォルト値を使用して分割するときに取得するフィールドの数は次のとおりです$IFS
。
printf '<%s> ' $cmd
<grep> <-i> <"word1"> <filename> <|> <grep> <-i> <"word2">
ファイル名の生成は次のことができます。
touch 'echo 1simple &&' 'echo 2simple'
eval echo*
答え2
私が使用する方法が間違っています。変えるすべてのコマンドを保存して実行します。より良い選択があります ——機能:
my_cmd() {grep -i "word1" filename | grep -i "word2"}
それはすべてです。
または、次のような他のパラメータを使用できます。
my_cmd() {grep -i "$1" "$3" | grep -i "$2"}
その後、電話で電話してください。
my_cmd word1 word2 filename
答え3
公開した例では評価は必要ありません。次のように変数を実行します。
cmd="grep -i \"word1\" filename | grep -i \"word2\""; # added missing " at the end
$cmd
あなたの提供に注意を払いなさい。たぶん、次のようなものはエラーが少なくなります。
cmd='grep -i "word1" filename | grep -i "word2"';