SuperCSV 読み込み時、カラム順序を動的に判断
SuperCSVには、読み込むファイルのカラム順序を適宜判断して、読み込む機能がありました。高機能ですね。
この機能を使うためには2つポイントが有りました。
- 読み込むファイルの1行目に、適切なカラム名称が記述されている必要があります。
- カラム名称と、Beanの項目、それからカラムの値を解析するCellProcessorとの対応付けを判断するロジックを記述します。
具体的には、次のようにして使うことができました。まず、読み込み処理です。ここでは、自分で作成したMeisaiCellProcessorsクラスを呼んでいるのがポイントです。
List<MeisaiBean> list = new ArrayList<MeisaiBean>(); BufferedReader br = new BufferedReader(new InputStreamReader(is)); ICsvBeanReader reader = new CsvBeanReader(br, CsvPreference.EXCEL_PREFERENCE); int count = 0; try { // ヘッダー部を読み込む count++; String[] header = reader.getCSVHeader(true); // データ部を読み込む MeisaiBean bean = null; MeisaiCellProcessors processors = new MeisaiCellProcessors(header); while (true) { count++; bean = reader.read(MeisaiBean.class, processors.getHeader(), processors.getCellProcessors()); if (bean == null) { break; } list.add(bean); } } catch (Exception e) { throw new RuntimeException("ファイル読み込みに失敗しました。行番号=[" + count + "]", e); } finally { reader.close(); }
MeisaiCellProcessorsクラスです。対象のBeanクラスには、XXXCellProcessorというプロパティ名(static)で、適切なCellProcessorが定義されている前提です。XXX部分は、カラム名称です。不要なカラムが存在する場合は、無視するようにしています。カラムが足りない場合には対応出来ていません。
import java.lang.reflect.Field; import java.util.ArrayList; import java.util.List; public class MeisaiCellProcessors { private List<String> header; private List<CellProcessor> cellProcessors; public MeisaiCellProcessors(String[] inFileHeader) { header = new ArrayList<String>(); cellProcessors = new ArrayList<CellProcessor>(); for (String columnName : inFileHeader) { try { String methodName = null; CellProcessor cp = null; if (columnName.length() > 0) { Class<MeisaiBean> c = MeisaiBean.class; Field f = c.getField(columnName.substring(0, 1) .toLowerCase() + columnName.substring(1) + "CellProcessor"); cp = (CellProcessor) f.get(null); methodName = columnName; } header.add(methodName); cellProcessors.add(cp); } catch (NoSuchFieldException e) { // 無視するカラムにはnullを入れる header.add(null); cellProcessors.add(null); } catch (Exception e) { throw new RuntimeException("ヘッダーの解析に失敗しました。name=[" + columnName + "]", e); } } } public String[] getHeader() { return header.toArray(new String[] {}); } public CellProcessor[] getCellProcessors() { return cellProcessors.toArray(new CellProcessor[] {}); } }
すいません。もう眠くなってきましたので、ここで終りとします。