文字列を取得し、次の文字列が見つかるまで行の先頭に置きます。

文字列を取得し、次の文字列が見つかるまで行の先頭に置きます。

私は、データをMySQLデータベースに保存するために必要な基本を繰り返すためにsed(約4回)を使用する大きな非標準のxhtmlファイルを持っています。私の最後の小さな闘争。このファイルの形式は次のとおりです。

 Tue Aug 18 2015
0,0,0,0,0
0,0,0,2,275
0,0,0,3,287
0,0,0,0,327
0,0,0,3,335
0,0,0,0,413
 Wed Aug 19 2015
0,0,0,0,0
0,0,0,2,275
0,0,0,3,287
0,0,0,2,308
 Thu Aug 20 2015
0,0,0,0,0
0,0,0,2,458
0,0,0,3,469
0,0,0,0,472
0,0,0,3,503
0,0,0,2,534

この日の前には常に空白があります。日付の後にCSV値の行が複数ある場合があります。

私が達成したいことは次のとおりです。

Tue Aug 18 2015,0,0,0,0,0
Tue Aug 18 2015,0,0,0,2,275
Tue Aug 18 2015,0,0,0,3,287
Tue Aug 18 2015,0,0,0,0,327
Tue Aug 18 2015,0,0,0,3,335
Tue Aug 18 2015,0,0,0,0,413
Wed Aug 19 2015,0,0,0,0,0
Wed Aug 19 2015,0,0,0,2,275
Wed Aug 19 2015,0,0,0,3,287
Wed Aug 19 2015,0,0,0,2,308
Thu Aug 20 2015,0,0,0,0,0
Thu Aug 20 2015,0,0,0,2,458
Thu Aug 20 2015,0,0,0,3,469
Thu Aug 20 2015,0,0,0,0,472
Thu Aug 20 2015,0,0,0,3,503
Thu Aug 20 2015,0,0,0,2,534

可能であれば、日付を削除してカンマを追加して、PHPスクリプトでより簡単に操作できるようにします。たとえば、次のようになります。

Aug,18,2015,0,0,0,0,0
Aug,18,2015,0,0,0,2,275
Aug,18,2015,0,0,0,3,287
Aug,18,2015,0,0,0,0,327
Aug,18,2015,0,0,0,3,335
Aug,18,2015,0,0,0,0,413
Aug,19,2015,0,0,0,0,0
Aug,19,2015,0,0,0,2,275
Aug,19,2015,0,0,0,3,287
Aug,19,2015,0,0,0,2,308
Aug,20,2015,0,0,0,0,0
Aug,20,2015,0,0,0,2,458
Aug,20,2015,0,0,0,3,469
Aug,20,2015,0,0,0,0,472
Aug,20,2015,0,0,0,3,503
Aug,20,2015,0,0,0,2,534

使用できるコマンドはありますか?

ベストアンサー1

1つの方法は次のとおりです。

sed '/,/!{                       # if there's no comma on this line
y/ /,/                           # translate spaces to commas
h                                # copy pattern space over the hold buffer
d                                # delete pattern space
}
//{                              # if the line contains commas
G                                # append hold space content to pattern space
s/\(.*\)\n,[^,]*,\(.*\)/\2,\1/   # swap lines removing newline, the day part and
}                                # first two commas and adding a comma after year
' infile

gnu sed1行を好む場合:

sed -E '/,/!{y/ /,/;h;d};//{G;s/(.*)\n,[^,]*,(.*)/\2,\1/}' infile

次のようになりますawk
行にカンマが含まれていない場合は、日付形式を指定してsprintf結果を変数(たとえば)に保存してから、dtログnextに移動して実行できます。それ以外の場合は、単に追加してくださいdt$0つまり、現在の行):

awk '!/,/{dt=sprintf("%s,%s,%s,", $2, $3, $4);next};$0=dt$0' infile

おすすめ記事