web-dev-qa-db-ja.com

エコー>>機能しない

これは私が段階的に達成しようとしていることです:

  1. ls
  2. 次に、出力を反転します
  3. 次に、このファイルの最後に新しい行を追加します

したがって、私は次の1行のスクリプトを作成しましたが、エラーが発生します

(ls | tac | echo >>) > ./foobar

これは複数のコマンドに分割することで実行できますが、1つのコマンドで実行しようとしています。

echo >> ./foobarファイルの終わりに新しい行を挿入します。

では、なぜ私のコード行が機能しないのですか?なぜ echo >>はファイル記述子の最後に改行を追加していませんが、代わりにエラーを出しますか?私はここで何が間違っているのですか?

1
GypsyCosmonaut

コマンドの解析方法は次のとおりです。

  • (…)は複合コマンドです。括弧の内容はサブシェルで実行されます。
    • ls | tac | echo >>は、lstac、およびecho >>の3つの部分で構成されるパイプラインです。左端の部分の出力は2番目の部分の入力に接続され、2番目の部分の出力は右端の部分の入力に接続されます。
    • lsは、実行可能ファイルを実行する単純なコマンドです。
    • tacは、実行可能ファイルを実行する単純なコマンドです。
    • echo >>は構文的に正しくありません。 >>演算子の後にファイル名を続ける必要があり、ファイル名がありません。
  • > ./foobarは、複合コマンドの出力をファイル./foobarにリダイレクトします。

入力をechoに送信しても意味がありません。つまり、入力を読み取りません。 echoを使用して他のコマンドの出力に追加するには、echoafterを実行します。平行。

ls | tac; echo

echoの出力はtacの出力と同じ場所に送られるため、リダイレクトする必要はありません。

( ls | tac; echo ) >./foobar

ここではサブシェルは必要ありません。単純なグループ化で十分です。 (bashの括弧のような演算子の要約については、 Bashの単純な論理演算子 を参照してください。)

{ ls | tac; echo; } >./foobar

>>演算子をappendに使用する必要があるのは、既存のファイルに追加する場合のみです。これはここでは当てはまりません。すべてのコマンドは同じ場所に移動し、ファイルfoobarは一度だけ開かれ、複合コマンド全体が実行されている限り開いたままになります。ファイルを2回開いた場合は、>>演算子が必要になります。

ls | tac >./foobar; echo >>./foobar

>>は、記号の直後のファイル名にコマンド出力を追加するようにシェルに指示します(したがって、少なくとも閉じ括弧の前に名前を追加する必要があります)。

あなたがしたいことのために、あなたは次のいずれかをすることができます:

ls | tac > ./foobar; echo >>./foobar

または:

(ls | tac; echo ) >./foobar

どちらも同じ結果を達成しています。

3
Folfy

指定された結果を達成するために、次のことが可能です。

echo -e "`ls | tac`\n" > ./foobar

このようにして、lsの出力はtacを介してパイプされます。結果はechoコマンドに含まれ、echoのエスケープ文字の解釈により改行が追加されます。その後、stdoutをファイルにリダイレクトできます。

Stdoutをechoにパイプすることは不可能だと思います。

2
KevinO