csv
データベースからエクスポートされた大容量ファイル(200万行)がありますSQL Server
。データベースにアクセスできませんR
。
サンプルデータは次のとおりです。
playerID,yearID,gameNum,gameID,teamID,lgID,GP,startingPos
gomezle01,1933,0,ALS193307060,NYA,AL,1,1
ferreri01,1933,0,ALS193307060,BOS,AL,1,2
gehrilo01,1933,0
,ALS193307060,NYA,AL,1,3
gehrich01,1933,0,ALS193307060,DET,AL,1,4
dykesji01,1933,0,ALS193307060,CHA,AL,1,5
cronijo01,1933,0,ALS193307060
,WS1,AL,1,6
chapmbe01,1933,0,ALS193307060,NYA,AL,1,7
simmoal01,1933,0,ALS193307060,CHA,AL,1,8
ruthba01,1933,0,ALS193307060,NYA,AL,1,9
上記のサンプルデータでは、一部の行が2つの行に分割されています。それをきれいにする方法?
修正する
- csv ファイルは Microsoft プラットフォームで生成されます。だから行は.で終わります
^m
。私はLinuxでサンプルデータを書きました\n
。明確にしなかったのは私のせいです。しかし、私はそれを代わりに\n
使用します\r\n
。 - 改行文字は常にカンマの前には表示されず、このようなフィールドでもランダムに表示されます。
。
Bill
Gates.
解決済み
ステップ1:^M
行の中央から削除します。
perl -pe 's/\r(?!\n)//g'
引用:https://stackoverflow.com/questions/6081465/how-to-remove-carriage-returns-in-the-middle-of-a-line
ステップ2:\n,
次に交換する,
(下記@jimmijの回答を参照)
perl -p00e 's/\n,/,/g'
ベストアンサー1
私たちはこれをテストファイルとして使います:
$ cat file
playerID,yearID,gameNum,gameID,teamID,lgID,GP,startingPos
gomezle01,1933,0,ALS193307060,NYA,AL,1,1
ferreri01,1933,0,ALS193307060,BOS,AL,1,2
gehrilo01,1933,0
,ALS193307060,NYA,AL,1,3
gehrich01,1933,0,ALS193307060,DET,AL,1,4
dykesji01,1933,0,ALS193307060,CHA,AL,1,5
cronijo01,1933,0,ALS193307060
,WS1,AL,1,6
chapmbe01,1933,0,ALS193307060,NYA,AL,1,7
simmoal01,1933,0,ALS193307060,CHA,AL,1,8
ruthba01,1933,0,ALS193307060,NYA,AL,1,9
Bill
Gates,1933,0,ALS193307060,NYA,AL,1,9
これにより、行が再び結合されます。
$ awk 'NR==1{printf "%s",$0; gsub(/[^,]/,""); nlast=n=length($0); next;} nlast==n{printf "\n";nlast=0} {printf "%s",$0; gsub(/[^,]/,""); nlast+=length($0)} END{print ""}' file
playerID,yearID,gameNum,gameID,teamID,lgID,GP,startingPos
gomezle01,1933,0,ALS193307060,NYA,AL,1,1
ferreri01,1933,0,ALS193307060,BOS,AL,1,2
gehrilo01,1933,0,ALS193307060,NYA,AL,1,3
gehrich01,1933,0,ALS193307060,DET,AL,1,4
dykesji01,1933,0,ALS193307060,CHA,AL,1,5
cronijo01,1933,0,ALS193307060,WS1,AL,1,6
chapmbe01,1933,0,ALS193307060,NYA,AL,1,7
simmoal01,1933,0,ALS193307060,CHA,AL,1,8
ruthba01,1933,0,ALS193307060,NYA,AL,1,9
BillGates,1933,0,ALS193307060,NYA,AL,1,9
行末の要件は明確ではありません。ここにコードを追加して処理できます。または、柔軟性を最大化するために必要に応じてdos2unix
ファイルを実行できますunix2dos
。
質問の最初のバージョンへの回答
大きな(200万行)csvファイルがあります。
以下は、ファイル全体を一度にメモリに読み込む必要のないラインベースのソリューションです。
$ awk 'NR>1 && !/^,/{printf "\n";} {printf "%s",$0} END{print ""}' file
playerID,yearID,gameNum,gameID,teamID,lgID,GP,startingPos
gomezle01,1933,0,ALS193307060,NYA,AL,1,1
ferreri01,1933,0,ALS193307060,BOS,AL,1,2
gehrilo01,1933,0,ALS193307060,NYA,AL,1,3
gehrich01,1933,0,ALS193307060,DET,AL,1,4
dykesji01,1933,0,ALS193307060,CHA,AL,1,5
cronijo01,1933,0,ALS193307060,WS1,AL,1,6
chapmbe01,1933,0,ALS193307060,NYA,AL,1,7
simmoal01,1933,0,ALS193307060,CHA,AL,1,8
ruthba01,1933,0,ALS193307060,NYA,AL,1,9
どのように動作しますか?
NR>1 && !/^,/{printf "\n";}
最初の行になく、
NR>1
現在の行がカンマで始まらない場合は、!/^,/
改行文字が印刷されます。{printf "%s",$0}
改行なしで現在の行を印刷します。
END{print ""}
ファイルの終わりに達すると、最後の行を終了するために別の改行文字が印刷されます。