Google
WWW を検索 tips.asablo.jp 内を検索
 このブログサイト(tips blog)の中だけを検索できます。
 アサブロへの設定方法は、こちらをクリック

PowerShellでCSVファイルを第1正規化する2017/04/30 07:45

コードサンプル
 PowerShellを使うと(コードさえ分かっていれば)CSVファイルを簡単に処理することができます。

 自分で一からCSVファイルを処理するなんて言ったらクソめんどくさいしバグまみれでやる気になりません。

 foreach ($l in Get-Content file.csv) {$l -split ","}
 するだけじゃない、と思われた方は、値に「,」や「"」が含まれている場合やセル内改行されている場合を想定してみましょう。

 PowerShellの場合にはImport-CSVとExport-CSVがあるので、簡単に処理できてしまいます。

 簡単な処理についてはselect-objectで記述できるのですが、1行処理して複数行を生成するような処理にはforeach-objectが必要ではないかと思います。

 問題はforeach-objectの処理結果をExport-CSVに渡す方法が不明だったこと。いえ、簡単に渡す方法が不明だったこと。



 以前参考にさせていただいたのはこちら
http://www.vwnet.jp/Windows/PowerShell/CreateCustomObject.htm

 できることはできるのですが、ちょっとコードがわかりにくい。3.0より前はこういう書き方しかできなかったのかもしれませんが。



 今回とても参考になったのはこちら
http://tech.guitarrapc.com/entry/2013/03/20/170321

 なるほど、ハッシュテーブルをキャスト一発でExport-CSVに渡せる形にできそうです。

 Export-CSVが PSCustomObject を処理する(できる?)というのはまた別のサイトで知った気がします。



 で、コードです。

[string]$uDesktop = [Environment]::GetFolderPath("Desktop")
[string]$uUnNormalizedFile = ( Join-Path $uDesktop "UnNormalized.csv" )
[string]$uNormalizedFile = ( Join-Path $uDesktop "Normalized.csv" )

Import-Csv $uUnNormalizedFile -Encoding Default |
ForEach-Object -Process {
for ( $i = 1; $i -le 10; $i++ )
{
$uRow = @{}

$uRow.請求書番号 = $_.請求書番号
$uRow.金額 = $_."金額$i"

[PSCustomObject]$uRow
}
} |
Export-Csv $uNormalizedFile -Encoding Default -NoTypeInformation

 元データはこんな感じ。
請求書番号,金額1,金額2,金額3,金額4,金額5,金額6,金額7,金額8,金額9,金額10
17-0001,100,101,102,103,104,105,106,107,108,109
17-0002,200,201,202,203,204,205,206,207,208,209

 処理結果はこんな感じ

"請求書番号","金額"
"17-0001","100"
"17-0001","101"
"17-0001","102"
"17-0001","103"
"17-0001","104"
"17-0001","105"
"17-0001","106"
"17-0001","107"
"17-0001","108"
"17-0001","109"
"17-0002","200"
"17-0002","201"
"17-0002","202"
"17-0002","203"
"17-0002","204"
"17-0002","205"
"17-0002","206"
"17-0002","207"
"17-0002","208"
"17-0002","209"

 無事に正規化できました。



 上記コードは漫然と正規化していますが、実際のコードの場合には、以下のように金額に値があるかどうかを判別することになるでしょう。


Import-Csv $uUnNormalizedFile -Encoding Default |
ForEach-Object -Process {
for ( $i = 1; $i -le 10; $i++ )
{
if ( $_."金額$i" -ne "" )
{
$uRow = @{}

$uRow.請求書番号 = $_.請求書番号
$uRow.金額 = $_."金額$i"

[PSCustomObject]$uRow
}
}
} |
Export-Csv $uNormalizedFile -Encoding Default -NoTypeInformation


 元データ
請求書番号,金額1,金額2,金額3,金額4,金額5,金額6,金額7,金額8,金額9,金額10
17-0001,100,101,102,103,104,105,106,,,
17-0002,200,201,202,203,204,,,,,


 結果
"請求書番号","金額"
"17-0001","100"
"17-0001","101"
"17-0001","102"
"17-0001","103"
"17-0001","104"
"17-0001","105"
"17-0001","106"
"17-0002","200"
"17-0002","201"
"17-0002","202"
"17-0002","203"
"17-0002","204"

コメント

コメントをどうぞ

※メールアドレスとURLの入力は必須ではありません。 入力されたメールアドレスは記事に反映されず、ブログの管理者のみが参照できます。

※なお、送られたコメントはブログの管理者が確認するまで公開されません。

※投稿には管理者が設定した質問に答える必要があります。

名前:
メールアドレス:
URL:
次の質問に答えてください:
スパム対策です。「BBB」と入力してください。なお、上記のメールアドレス、URLは不要です。

コメント:

トラックバック

Google
WWW を検索 tips.asablo.jp 内を検索
 このブログサイト(tips blog)の中だけを検索できます。
 アサブロへの設定方法は、こちらをクリック