VBA Stepup13
第13章 CSVファイル取込サンプル
CSVデータを取込、CSVデータの項目から他のブックにあるデータを付加して、編集した新しいブックに名前を付けて保存する、という一連の処理をVBAで作成すると、この章のようなソースコードになります。CSVデータは、ETCの利用明細のフォーマットで、カード番号に対応した所属や氏名を付加します。
'変数の定義
Dim varFileName As Variant
Dim txtArray As Variant
Dim intFree As Integer
Dim strRec As String
Dim wb As Workbook
Dim ws As Worksheet
Dim nwb As Workbook
Dim nws As Worksheet
Dim CurrentPath As String
Dim saveName As String
Dim i As Long, j As Long, k As Long, l As Long
'ファイルを開くのダイアログを表示し、CSVファイルを選択させる
varFileName = Application.GetOpenFilename(_
FileFilter:="テキストファイル(*.csv),*.csv", _
Title:="CSVファイルの選択")
'CSVファイルが選択されていない場合は、処理を中断する
If varFileName = False Then
Exit Sub
End If
'CSVファイルをExcelで読み込み可能状態にする
intFree = FreeFile '空番号を取得
Open varFileName For Input As #intFree 'テキストファィルをオープン
'編集後のExcelファイルを保存するときの、ファイルのパスを取得する(マクロを実行しているファイルのパス)
CurrentPath = ThisWorkbook.Path
'オブジェクト変数wbに、ブック名ETCxxxxx.xlsxをセットする
Set wb = Workbooks.Open(Filename:=CurrentPath & _
"\ETCxxxxx.xlsx")
'オブジェクト変数wsに、ブック名「ETCxxxxx.xlsx」のシート名の「カード利用者」をセットする
Set ws = wb.Worksheets("カード利用者")
'オブジェクト変数nwbに、新規ブックをセットする
Set nwb = Workbooks.Add
'オブジェクト変数nwsに、新規ブックの一番左のシートをセットする
Set nws = nwb.Worksheets(1)
i = 1
'CSVファイルのテキストデータを1行ずつ読み込み、テキストデータが終わるまで繰り返す
Do Until EOF(intFree)
Line Input #intFree, strRec '1行読み込み
'CSVデータの1行分をカンマで分割して、配列の変数に代入する
txtArray = Split(strRec, ",")
'1行目はタイトル行なので、必要な項目を配列からセルに代入する
If i = 1 Then
nws.Cells(i, 1) = txtArray(1)
nws.Cells(i, 1).HorizontalAlignment = xlCenter
'1行目の2列目から5列目まではETCカード.xlsxのカード利用者のシートの1行目から項目名を代入する
For j = 2 To 5
nws.Cells(i, j) = ws.Cells(1, j)
nws.Cells(i, j).HorizontalAlignment = xlCenter
Next
nws.Cells(i, 6) = txtArray(3)
For j = 7 To 12
If j > 10 Then
nws.Cells(i, j) = txtArray(j - 1)
Else
nws.Cells(i, j) = txtArray(j - 2)
End If
nws.Cells(i, j).HorizontalAlignment = xlCenter
Next
'2行目以降はデータ行なので、文字列にするセルには表示形式を文字列(@)にする
Else
nws.Cells(i, 1).NumberFormat = "@"
nws.Cells(i, 1) = txtArray(1)
'2列目から5列目まではETCカード.xlsxのカード利用者からカード番号に該当する部門~氏名を代入する
For k = 2 To ws.Cells(2, 1).End(xlDown).Row
If txtArray(1) = ws.Cells(k, 1) Then
For j = 2 To 5
nws.Cells(i, j) = ws.Cells(k, j)
Next
Exit For
End If
Next
'日付のデータは日付のシリアル値に変換して表示形式を日付に設定する
nws.Cells(i, 6) = Format(DateSerial(Left(txtArray(3), 4), _
Mid(txtArray(3), 5, 2), Right(txtArray(3), 2)), _
"yyyy/m/d")
For j = 7 To 12
If j > 10 Then
nws.Cells(i, j) = Format(txtArray(j - 1), "#,##0")
Else
nws.Cells(i, j).NumberFormat = "@"
nws.Cells(i, j) = txtArray(j - 2)
End If
Next
End If
i = i + 1
Loop
'CSVデータが1件以上あった場合は、列幅を自動調整して、格子線を引く
If i > 1 Then
For l = 1 To 12
nws.Columns(l).AutoFit
Next
nws.Range("A1").CurrentRegion.Borders.LineStyle = _
xlContinuous
'システム日付からファイル名に年月日を付加したファイル名を生成して、名前を付けて保存をする
saveName = Year(Date) & Format(Month(Date), "00") & _
Format(Day(Date), "00") & "ETCデータ.xlsx"
nwb.SaveAs Filename:=CurrentPath & "\" & saveName
End If
'CSVファイルとETCxxxxx.xlsxを閉じて、ETCxxxxx.xlsxのオブジェクト変数を開放する
Close #intFree
wb.Close
Set wb = Nothing
Set ws = Nothing
Set nwb = Nothing
Set nws = Nothing
CSVデータを全件読み込むため、変数iはCSVファイルのデータ行と新規ブックの編集シートの行数を示します。CSVデータの項目で必要なものを、配列から取り出します。CSVデータのレイアウトにより、配列からの取り出し場所が変わります。
コメント付きのソースでやや見づらいかもしれませんが、このソースコードが読めるようになると、VBAに関してはある程度のレベルに達して、実務に役立つプログラムが組めるようになります。
アクティブブック以外のブックやアクティブシート以外のシートを操作するときに、オブジェクト変数を使うとコーディング作業も楽になります。
VBA応用編がすべて理解できましたら、このようなプログラムが組めるようになります。CSVデータを取り込んで、既存のExcelデータからデータを付加する業務は実用的で、しかも事務作業の負担になっています。これを手作業で行うと半日近くはかかってしまいます。事務作業は合理化すれば時間短縮出来る作業です。ExcelのVBAを活用して、日々の業務を楽にする努力をしていただけたらと思っております。