私はかなり長い間sed
を使用してきましたが、ここで私が思いついた問題を解決できません。
実際のケースで私の問題を説明しましょう。
シーン#1
printf "ls" | xclip -selection clipboard
echo "ls" | xclip -selection clipboard
最初のコマンドでは、printf
出力をxclip
にパイプして、クリップボードにコピーされるようにします。 printf
とは異なり、echo
はデフォルトで末尾に新しい行を挿入しません。そのため、このコンテンツをターミナルに貼り付けても、コピーされたls
コマンドは自動的に実行されません。
2番目では、最後に新しい行があるので、クリップボードの内容を貼り付けると、クリップボードでコマンドが実行されます。
これは私には望ましくありません。そのため、sed
を使用して改行を削除したかったのですが、以下のシーンで説明されているように、失敗しました。
シーン#2
echo "ls" | sed -r 's/\n//g' | xclip -selection clipboard
クリップボードのコンテンツにはまだ改行が含まれています。端末に貼り付けると、コマンドが自動的に実行されます。
改行文字\r
も削除してみました。なだ。ここに非常に重要な/基本的な何かが欠けているようです。
sed
は\n
ewlinesで区切られます-それらは常に入力時に削除され、出力時に再挿入されます。 neversed
パターンスペースに\n
ewline文字がありますが、これは、行った編集の結果としては発生しませんでした。 注:GNU sed
's -z
mode ...を除いて...
tr
を使用するだけです:
echo ls | tr -d \\n | xclip -selection clipboard
または、さらに良いことに、sed
を完全に忘れてください:
printf ls | xclip -selection clipboard
Sedを含む多くのテキスト処理ツールは、改行文字を除いて、行のコンテンツを操作します。行を処理するときに最初にsedが行うのは、最後の改行を取り除くことです。次に、スクリプト内のコマンドを実行し、印刷時に最後の改行を追加します。したがって、sedを使用して改行を削除することはできません。
すべての改行を削除するには、代わりにtr
を使用できます。
echo "ls" | tr -d '\n' | xclip
-zオプションを渡すことで、sedの改行を置き換えることができます。
sed -z 's/\n/ /g'
Sedのmanページ:
-z、--null-data行をNUL文字で区切る
コマンドをクリップボードに置くだけの場合
echo -n "ls " | xclip -selection clipboard
さらに複雑な変換を行う必要がある場合は、
echo "ls " | Perl -pe 's/\n//' | xclip -selection clipboard
最後の改行のみを削除するには、次のようにパイプします。
sed -z '$ s/\n$//'
区切り文字がsed
に\0
を介して設定されている場合、NUL
は-z
をストリームの最後に追加しませんが、POSIXテキストファイル(定義済み\n
で終わるために、常に\n
なしで最後の-z
を出力します。
例えば:
$ { echo foo; echo bar; } | sed -z '$ s/\n$//'; echo tender
foo
bartender
そしてNUL
が追加されていないことを証明するために:
$ { echo foo; echo bar; } | sed -z '$ s/\n$//' | xxd
00000000: 666f 6f0a 6261 72 foo.bar
複数の末尾の改行を削除するには、パイプスルーします。
sed -Ez '$ s/\n+$//'