GNU/Linux >> Linux の 問題 >  >> Linux

Linux:ファイルを入力と出力として同時に使用する方法は?

解決策 1:

echo "$(uniq .bash_history)" > .bash_history

望ましい結果が得られるはずです。サブシェルは .bash_history の前に実行されます 書き込み用に開いています。 Phil Pの回答で説明されているように、 .bash_history までに 元のコマンドで読み込まれ、> によって既に切り捨てられています。

解決策 2:

sponge の使用をお勧めします moreutils から。マンページから:

DESCRIPTION
  sponge  reads  standard  input  and writes it out to the specified file. Unlike
  a shell redirect, sponge soaks up all its input before opening the output file.
  This allows for constructing pipelines that read from and write to the same 
  file.

これをあなたの問題に適用するには、以下を試してください:

uniq .bash_history | sponge .bash_history

解決策 3:

問題は、コマンドを実行する前にシェルがコマンド パイプラインを設定していることです。 「入力と出力」の問題ではなく、 uniq が実行される前にファイルの内容がすでになくなっているということです。次のようになります:

<オール>
  • シェルは > を開きます 書き込み用の出力ファイル、切り捨て
  • シェルは、ファイル記述子 1 (stdout 用) がその出力に使用されるように設定します
  • シェルは、おそらく execlp("uniq", "uniq", ".bash_history", NULL) のような uniq を実行します
  • uniq が実行され、.bash_history が開かれ、そこには何も見つかりません
  • 他の人が言及しているインプレース編集や一時ファイルの使用など、さまざまな解決策がありますが、重要なのは、問題、実際に何がうまくいかないのか、その理由を理解することです.

    解決策 4:

    sponge を使用せずにこれを行う別のトリック 、次のコマンドです:

    { rm .bash_history && uniq > .bash_history; } < .bash_history
    

    これは、backreference.org のファイルの優れた記事「インプレース」編集で説明されているチートの 1 つです。

    基本的に、ファイルを読み取り用に開き、「削除」します。ただし、実際には削除されたわけではありません。それを指す開いているファイル記述子があり、それが開いている限り、ファイルは引き続き存在します。次に、同じ名前で新しいファイルを作成し、一意の行を書き込みます。

    このソリューションの欠点:uniq の場合 何らかの理由で失敗すると、履歴が失われます。

    解決策 5:

    moreutils のスポンジを使用

    uniq .bash_history | sponge .bash_history
    

    Linux
    1. LinuxでTarコマンドを使用する方法

    2. LinuxTouchコマンドの使用方法+例

    3. ファイルをコピーすると同時にターゲットディレクトリを作成するにはどうすればよいですか?

    1. Linuxスクリプトコマンドを使用してターミナルセッションをキャプチャして出力する方法

    2. Stdoutに出力し、同時にGrepをファイルに出力しますか?

    3. ターミナルの入力と出力をテキストファイルに取得する方法は??

    1. Linuxでエイリアスを作成してエイリアスコマンドを使用する方法

    2. Linuxで出力をファイルとStdoutにリダイレクトする方法

    3. time コマンドの出力を Linux のファイルにリダイレクトする方法は?