改行で区切られたパラメータを読む

改行で区切られたパラメータを読む

標準入力のデータを改行文字で区切られた引数として受け取るスクリプトがあります。

string1,string2
string3,string4

string1,string2とは別に持ちたいですstring3,string4。しかし、不明な数のそのような行を受け取り、私のスクリプトは最初の2行だけを読んでから停止します。標準入力で解析しようとしましたが、\n動作しません。この問題にどのように対処する必要がありますか?

私はこのように読もうとする

for i in "$@" 
do 
var1=$(echo "$i" | cut -f2 -d,) 
var2=$(echo "$i" | cut-f2 -d,)
#etc

input.txt私が実際に達成したいのは、次のタイプの入力を含むファイルがあると仮定することです。

string1,string2
string3,string4

これにより、文字列の行数に関係なく各行を取得し、両方の変数から別々に抽出したいとcat input.txt | ./myscript.sh思います。stringI,stringJ

答え1

テキスト処理を実行したい場合は、最も明確な方法は、awkこの目的のために特別に設計されたものを使用することです(または使用することもできますperl)。sed

awk -F, '{print "something with "$1" and "$2}'

入力が実際のCSVの場合、次のようにより複雑な値を持つことができます。

"field, with comma" , "and with
newline", "or ""quotes"""

専用のcsv解析ユーティリティを使用perlしたい場合があります。python

たとえば、これらのフィールドを引数として使用して特定のコマンドを実行する必要があるため、これらのフィールドをシェル変数として指定する必要がある場合は、次のようにします。

while IFS=, read -r a b rest; do
   something-with "$a" "$b"
done

GNUparallel並列実行も参照してください。

PARALLEL_SHELL=sh parallel -C, 'something-with {1} {2}'

しかし、GNUはparallelかなりのオーバーヘッドを引き起こすので、並列化はそれほど価値があるはずです。

シェルはksh93実際にCSV形式を理解します(上記の複雑な例のように個々のフィールドへの参照を処理します)。

while IFS=, read -rS a b rest; do
   do-something-with "$a" "$b"
done

答え2

複数行のユーザー入力を取得するには、-dオプションを指定してreadを使用することをお勧めします。

または、tr '\n' ' '新しい行を空白に変換する方法を使用します。これはかなりハッキーです。

私は方法がわかりませんが、trを使用してEOFを新しい行に変換すると、期待どおりに完全に実行できます。

より具体的な情報が必要な場合はコメントを残してください。

答え3

(何らかの理由で)すべての入力ラインを配列に配置するには、bashで次のように使用できます。

readarray -t input_lines

その後、各行はインデックス配列の要素として保存されますinput_lines-t各行から改行文字を削除することです。

関連情報