私の Bash 課題の一部には、テキスト ファイルを読み取り、各行を単語に分割して使用することが含まれます。
単語は で区切られ|
、行は で区切られ\n
ます。コマンドを使用するように言われましたがtr
、エレガントな解決策が見つかりませんでした。
例:
Hello | My | Name | Is | Bill
与えるべき:
Hello
My
Name
Is
Bill
反復ごとに 1 語。
tr
このジョブを実行するには、 を1 回呼び出すだけです。
$ echo "Hello | My | Name | Is | Bill" | tr -cs '[:alpha:]' '\n'
Hello
My
Name
Is
Bill
$
オプションは、最初のパターンの文字の-c
「補数」です。この-s
オプションは、重複する置換文字を「絞り出します」。したがって、アルファベット順でないものはすべて改行に変換されますが、連続する改行は 1 つの改行に圧縮されます。
明らかに、「他のすべてのユーザーを維持する必要がある場合 | できます | コール | 私 | 私 | 出力の最初の行にある 2 つの単語で Fred' を入力すると、かなりの作業が必要になります。
$ echo "Everyone else | can | call | me | Fred" |
> tr '|' '\n' |
> sed 's/ *$//;s/^ *//'
Everyone else
can
call
me
Fred
$
このsed
スクリプトは、先頭と末尾の空白を削除し、中間の空白を変更しません。必要に応じて、複数の空白を 1 つの空白に置き換えることができます。特定の文字を条件付きで置換するために を使用することはできませんtr
(たとえば、一部の空白を変更し、他の空白をそのままにするなど)。
tr の使用:
echo "Hello | My | Name | Is | Bill" | tr -s '\| ' '\n'
または、 awk にチャンスを与えることにした場合:
echo "Hello | My | Name | Is | Bill" | awk -F '\|' '{for (i=1; i<=NF; i++) {
sub(/ /, "", $i); print $i}}'
その他のオプション:
awk:
awk -F'\\| ' -v OFS="\n" '$1=$1'
例:
kent$ echo "Hello | My | Name | Is | Bill" |awk -F'\\| ' -v OFS="\n" '$1=$1'
Hello
My
Name
Is
Bill
grep
grep -o '[^ |]*'
例:
kent$ echo "Hello | My | Name | Is | Bill"|grep -o '[^ |]*'
Hello
My
Name
Is
Bill
シード
sed 's/ | /\n/g'
例:
kent$ echo "Hello | My | Name | Is | Bill" |sed 's/ | /\n/g'
Hello
My
Name
Is
Bil
私のお気に入りのパール:)
echo "Hello | My | Name | Is | Bill" | perl -pe 's/\s*\|\s*/\n/g'
余分なスペースも削除されるので、
echo "Hello | My | Name | Is | Bill" | perl -pe 's/\s*\|\s*/\n/g' | cat -vet
印刷します
Hello$
My$
Name$
Is$
Bill$
このコードはそれを行う必要があり、「|」を変換します 改行するには、先頭/末尾のスペースを削除します:
echo "Hello | My | Name | Is | Bill" | tr '|' '\n' | tr -d [:blank:]
ファイル一時: こんにちは | 私の| 名前 | です | 明細書
$ cat temp | tr '|' '\n' | sed 's/^ *//g'
Hello
My
Name
Is
Bill
$
sed の部分は、先頭のスペースを取り除きます ('|' と単語の間にスペースがあるためです。これは、"Hello everyone | My | Name | Is | Bill" に対しても機能します。
$ cat temp | tr '|' '\n' | sed 's/^ *//g'
Hello everyone
My
Name
Is
Bill
$