【VBA】CSV読み込み。カンマを含む文字データをsplitで分割する。
CSVの文字データにカンマが含まれる場合
1,"カンマ,を含む文字" |
これをVBAで読み込もうとする場合、Splitで単純にカンマ分割するとこんな感じの分割になってしまいます。
1列目:1 2列目:"カンマ 3列目:を含む文字" |
これをSplitで何とかやろうとする場合のサンプル。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 |
Sub main() Dim InFilePath As String '入力ファイルパス Dim i, j As Integer Dim str As String Dim splitString As Variant InFilePath = ActiveWorkbook.Path & "\testdata.csv" Open InFilePath For Input As #1 'ファイル読み込み Do While Not EOF(1) Line Input #1, str splitString = csvSplit(str) For j = 0 To UBound(splitString) - 1 Debug.Print i + 1 & "行目 " & j + 1 & "列目 : " & splitString(j) Next j i = i + 1 Loop Close #1 End Sub 'カンマ区切り分割処理 Function csvSplit(ByVal str As String) As Variant Dim i As Integer Dim arrayCnt As Integer Dim s As String '1文字分 Dim data As String '1データ分 Dim doubleQuoteFlag As Boolean 'True=ダブルクォートの中、False=ダブルクォートの外 Dim retArray() As String For i = 1 To Len(str) '1文字ずつ判定 s = Mid(str, i, 1) If s = """" Then 'ダブルクォートの場合、中⇔外を反転 doubleQuoteFlag = Not doubleQuoteFlag ElseIf s = "," And doubleQuoteFlag Then 'ダブルクォートの中のカンマはデータとして扱う data = data & s ElseIf s = "," And Not doubleQuoteFlag Then 'ダブルクォートの外のカンマ発見で区切り arrayCnt = arrayCnt + 1 ReDim Preserve retArray(arrayCnt) retArray(arrayCnt - 1) = data data = "" Else data = data & s End If Next i If Not data = "" Then '最終列のデータを配列に格納 arrayCnt = arrayCnt + 1 ReDim Preserve retArray(arrayCnt) retArray(arrayCnt - 1) = data End If csvSplit = retArray End Function |
実行結果がこちら。
testdata.csv 1,"テスト1行目" 2,"テスト,2行目" |
出力結果 1行目 1列目 : 1 1行目 2列目 : テスト1行目 2行目 1列目 : 2 2行目 2列目 : テスト,2行目 |
ちなみに上記サンプルコードは、下記に書き換えることもできます(書き方が適当なので、少し汎用性が無くなりますが・・)。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 |
Sub main() Dim InFilePath As String '入力ファイルパス Dim i As Integer Dim col1, col2 As String 'ファイル選択ダイアログ InFilePath = ActiveWorkbook.Path & "\testdata.csv" Open InFilePath For Input As #1 '入力ファイル読み込み→出力ファイル書き込み Do While Not EOF(1) Input #1, col1, col2 Debug.Print i + 1 & "行目 " & "1列目 : " & col1 Debug.Print i + 1 & "行目 " & "2列目 : " & col2 i = i + 1 Loop Close #1 End Sub |
Line Inputで行を抜き出さなくてもInputで値を抜き出せば、文字データに含まれるカンマもちゃんと文字として扱ってくれるようです。タブ区切りもこれでイケるみたいですね。