CSVの文字データにカンマが含まれる場合
1,”カンマ,を含む文字” |
これをapexで読み込む際、Splitで単純にカンマ分割するとこんな感じの読み込みになってしまいます。
1列目:1 2列目:”カンマ 3列目:を含む文字” |
ダブルクォーテーションで囲まれたカンマを文字として扱いたい場合、apexでは現時点でAPIが用意されていないようなので(多分..)、1文字ずつ判定する必要があります。
サンプルはこんな感じになります。
1行分のデータを食わせると、カンマで分割したデータをリストに突っ込んで返してくれるメソッドです。
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 |
/** * CSVカンマ区切り分割処理. * データにカンマを含み単純にsplitできない場合に対応 * @param line 1行分データ * @return 分割したデータリスト */ public List<String> csvSplit(String line) { List<String> retList = new List<String>(); String data = ''; //1データ分 Boolean doubleQuoteFlag = False; //True=ダブルクォートの中、False=ダブルクォートの外 For (Integer i = 0; i < line.length(); i++) { // 1文字ずつ判定 String s = line.mid(i, 1); If (s.equals('"')) { // ダブルクォートの場合、中⇔外を反転 doubleQuoteFlag = !doubleQuoteFlag; } else if (s.equals(',') && doubleQuoteFlag) { // ダブルクォートの中のカンマはデータとして扱う data += s; } else if (s.equals(',') && !doubleQuoteFlag) { // ダブルクォートの外のカンマ発見で区切り retList.add(data); data = ''; } else { data += s; } } // 最終列のデータをリストに設定 retList.add(data); return retList; } |
なお上記サンプルはダブルクォーテーションのエスケープには対応していません・・。あしからず。
囲みのダブルクォーテーションはついでに取っ払っています。
デバッグモードで動作確認します。
1 2 3 4 5 6 7 8 |
/** 動作確認コード */ String line = '1,"カンマ,を含む文字"'; TestClass test = new TestClass(); List<String> cols = test.csvSplit(line); for (Integer i = 0; i < cols.size(); i++) { System.debug((i + 1) + '列目:' + cols.get(i)); } |
期待とおりの動作になりました!
USER_DEBUG [6]|DEBUG|1列目:1 USER_DEBUG [6]|DEBUG|2列目:カンマ,を含む文字 |
コメント