1

我正在使用 supercsv CsvBeanWriter 将值写入 csv 文件。

样本类:

public class Employee {
    private String name;

    private int empId;

    List<String> phoneNumbers;
}

我得到的输出是:

name,empId,phoneNumbers
vijay,1,"[123, 456]"

请注意如何List<String> phoneNumbers写出[]

我的问题是如何使用 supercsv 将其读回 Employee 类(bean)。

我尝试使用CsvBeanReader&CsvDozerBeanReader但无法读取List<String>.

我得到了非法参数异常。将感谢任何指点!

完整代码:

public class DozerBeanReader {
public static void main(String [] args){
    ICsvDozerBeanReader beanReader = null;

    try {
        beanReader = new CsvDozerBeanReader(new FileReader("Employee.csv"), 
                CsvPreference.STANDARD_PREFERENCE);

        String [] header = beanReader.getHeader(true); // ignore the header

        Class<?> [] hintTypes = {String.class, Integer.class, List.class};

        beanReader.configureBeanMapping(Employee.class, header, hintTypes);

        Employee readEmp1 = beanReader.read(Employee.class);
        readEmp1.toString();
    } catch (FileNotFoundException e) {
        // TODO Auto-generated catch block
        e.printStackTrace();
    } catch (IOException e) {
        // TODO Auto-generated catch block
        e.printStackTrace();
    }


}
}
4

1 回答 1

1

您依赖于这样一个事实,即您的电话号码使用列表的格式List写入单个 CSV 列,例如.toString()[123, 456]

您将收到类似以下内容的异常:

org.dozer.MappingException: Illegal object type 
for the method 'setPhoneNumbers'. 
Expected types: 
java.util.List
Actual types: 
java.lang.String

因为 Dozer 不知道如何将 String 转换[123, 456]List. 您可以这样做,但您需要编写一个单元处理器来将该 String 转换回List. 如果您的电话号码是纯数字,那应该不会太难,但是如果您的电话号码有逗号,那么事情就会变得一团糟!

我建议将每个电话号码写成一个单独的列 - 这样会更容易(对于任何阅读您文件的人,包括您!)。

您需要做的就是使用带有索引映射的 CsvDozerBeanReader 和 CsvDozerBeanWriter 。

这是一个示例 - 关键部分是索引映射:

String[] fieldMapping = new String[] { "name",
    "empId", "phoneNumbers[0]", "phoneNumbers[1]" };
  • 我已经定义了 2 个电话号码列 - 如果您的列表会有更多,那么只需添加更多列
  • 我本可以使用 fieldMapping 作为标题,但选择使用更具可读性的自定义标题
  • 您不需要问题中的提示
  • 我使用 StringReader/StringWriter 只是为了简化示例

例子:

// create employee to write/read
Employee employee = new Employee();
employee.setEmpId(1234);
employee.setName("Vijay");
employee.setPhoneNumbers(Arrays.asList("123", "456"));

// the CSV header
String[] header = new String[] { "name",
    "empId", "phoneNumber1", "phoneNumber2" };

// the field mapping
String[] fieldMapping = new String[] { "name",
    "empId", "phoneNumbers[0]", "phoneNumbers[1]" };

// write the employee
StringWriter out = new StringWriter();
ICsvDozerBeanWriter writer = 
    new CsvDozerBeanWriter(out,
    CsvPreference.STANDARD_PREFERENCE);
writer.configureBeanMapping(Employee.class, fieldMapping);
writer.writeHeader(header);
writer.write(employee);
writer.flush();

// read the employee
ICsvDozerBeanReader reader = 
    new CsvDozerBeanReader(new StringReader(out.toString()),
    CsvPreference.STANDARD_PREFERENCE);
reader.configureBeanMapping(Employee.class, fieldMapping);
reader.getHeader(true); // ignore header
Employee e = reader.read(Employee.class);
System.out.println(e);

假设您已经编写了toString()方法,这应该打印

Employee [name=Vijay, empId=1234, phoneNumbers=[123, 456]]
于 2014-01-16T12:31:15.590 回答