[java]Super CSV で区切り文字や改行文字を任意に指定する
「で、区切り文字とかどうなってんの?」
はい、ちゃんと用意されています。CsvPreferenceというクラスで指定できます。
次のように第2引数で指定します。
ICsvBeanReader inFile = new CsvBeanReader(new FileReader("./data/foo.csv"), CsvPreference.EXCEL_PREFERENCE); ICsvMapWriter writer = new CsvMapWriter(new FileWriter("./data/boo.csv"), CsvPreference.EXCEL_PREFERENCE);
CsvPreference.EXCEL_PREFERENCEを使用していますが、予め用意されている定義は全部で4種類。
定数名称 | クォート文字 | 区切り文字(デリミタ) | 改行文字 |
---|---|---|---|
STANDARD_PREFERENCE | " | , | \r\n |
EXCEL_PREFERENCE | " | , | \n |
EXCEL_NORTH_EUROPE_PREFERENCE | " | ; | \n |
NO_COMMENT_PREFERENCE | " | , | \n |
何気にEXCEL_PREFERENCEとNO_COMMENT_PREFERENCEは、定義内容が全く同じです。
さて、当然これ以外のパターンについても任意で指定することが可能です。たとえば、クォート文字を'B'、区切り文字を'?'、改行文字列を"\r\n"としたい場合、
CsvPreference preference = new CsvPreference('B', '?', "\r\n"); ICsvBeanReader inFile = new CsvBeanReader(new FileReader("./data/foo.csv"), preference); ICsvMapWriter writer = new CsvMapWriter(new FileWriter("./data/boo.csv"), preference);
といった要領でCsvPreferenceをインスタンス化し、使用します。
[java]Super CSV による File Read
Super CSVは、CSVファイルをオブジェクトのような感覚で扱うことができる、オープンソースのCSVファイル高速アクセスライブラリです。言ってみればO/RマッピングのCSVファイル版ですね。
http://supercsv.sourceforge.net/
これが非常に便利そうなのに、何故かサイトに載っているサンプルコードが微妙に不親切なので、簡単に書き換えてみました。
読み込むCSVファイルの内容は次のような感じです。
ファイル名:foo.csv
username, password, date, zip, town Klaus, qwexyKiks, 17/1/2007, 1111, New York Oufu, bobilop, 10/10/2007, 4555, New York
さて、まずはBeanの定義。このクラスでは、CSVファイルの列要素を定義します。
ファイル名:UserBean.java
package bean; import java.util.Date; import org.supercsv.cellprocessor.Optional; import org.supercsv.cellprocessor.ParseDate; import org.supercsv.cellprocessor.ParseInt; import org.supercsv.cellprocessor.constraint.StrMinMax; import org.supercsv.cellprocessor.constraint.Unique; import org.supercsv.cellprocessor.ift.CellProcessor; /** * CSVファイルの要素定義(Bean) * @author kazuki.kido */ public class UserBean { /** 各要素フォーマット定義 */ public static final CellProcessor[] processors = new CellProcessor[] { new Unique(new StrMinMax(4, 20)), // username new StrMinMax(7, 35), // password new ParseDate("dd/MM/yyyy"), // date new Optional(new ParseInt()), // zip null // town }; /* 各要素の Getter/Setter 定義 */ private String username, password, town; private Date date; private int zip; public String getPassword() { return password; } public Date getDate() { return date; } public String getTown() { return town; } public String getUsername() { return username; } public int getZip() { return zip; } public void setPassword(String password) { this.password = password; } public void setDate(Date date) { this.date = date; } public void setTown(String town) { this.town = town; } public void setUsername(String username) { this.username = username; } public void setZip(int zip) { this.zip = zip; } }
で、実際に読み込み処理を行うmain実装が↓のようなかんじになります。読み込んだ内容をコンソール出力します。
ファイル名:ReadingObjects.java
package read; import java.io.FileReader; import org.supercsv.io.CsvBeanReader; import org.supercsv.io.ICsvBeanReader; import org.supercsv.prefs.CsvPreference; import bean.UserBean; /** * SuperCSVによるCSVファイル読み込み * @author kazuki.kido */ public class ReadingObjects { public static void main(String[] args) throws Exception{ ICsvBeanReader inFile = new CsvBeanReader( new FileReader("./data/foo.csv"), CsvPreference.EXCEL_PREFERENCE); try { final String[] header = inFile.getCSVHeader(true); UserBean user = null; while((user = inFile.read(UserBean.class, header, UserBean.processors)) != null){ // 取得要素をコンソールへ出力 System.out.print("ユーザ名:" + user.getUsername()); System.out.print(" パスワード:" + user.getPassword()); System.out.print(" 日付:" + user.getDate()); System.out.print(" 郵便番号:" + user.getZip()); System.out.println(" 住所:" + user.getTown()); } } finally { inFile.close(); } } }
で、コンソール出力結果がこんなかんじになります。
ユーザ名:Klaus パスワード:qwexyKiks 日付:Wed Jan 17 00:00:00 JST 2007 郵便番号:1111 住所:New York
ユーザ名:Oufu パスワード:bobilop 日付:Wed Oct 10 00:00:00 JST 2007 郵便番号:4555 住所:New York
Beanを介してCSVファイルの内容を簡単に取得できます。定義に沿ってDate型なんかに自動変換してくれるので、とても楽です。
[java]Super CSV による File Write
では続いてファイル書き込みもやってみましょう。
ファイル名:WritingMaps.java
package write; import java.io.FileWriter; import java.util.HashMap; import org.supercsv.io.CsvMapWriter; import org.supercsv.io.ICsvMapWriter; import org.supercsv.prefs.CsvPreference; /** * SuperCSVによるCSVファイル書き込み * @author kazuki.kido */ class WritingMaps { public static void main(String[] args) throws Exception { ICsvMapWriter writer = new CsvMapWriter(new FileWriter("./data/boo.csv"), CsvPreference.EXCEL_PREFERENCE); try { final String[] header = new String[] { "name", "city", "zip" }; // 1行目データを作成 final HashMap<String, ? super Object> data1 = new HashMap<String, Object>(); data1.put(header[0], "Karl"); data1.put(header[1], "Tent city"); data1.put(header[2], 5565); // 2行目データを作成 final HashMap<String, ? super Object> data2 = new HashMap<String, Object>(); data2.put(header[0], "Banjo"); data2.put(header[1], "River side"); data2.put(header[2], 5551); // ファイルへ出力 writer.writeHeader(header); writer.write(data1, header); writer.write(data2, header); } finally { writer.close(); } } }
こちらはBeanではなく、Mapを用いています。当然、ICsvBeanWriter, CsvBeanWriterとUserBeanを使えば、Beanによる書き込みも可能です。
[java]CsvBeanReader, CsvBeanWriter, ParseDateを併用するには - Undead mode 忘備録
ファイルへの出力結果は次の通り。
ファイル名:boo.csv
name,city,zip Karl,Tent city,5565 Banjo,River side,5551
よさげです。