为了账号安全,请及时绑定邮箱和手机立即绑定

使用FlatFileItemReader读取csv文件,遇到空列时抛出异常

使用FlatFileItemReader读取csv文件,遇到空列时抛出异常

Smart猫小萌 2023-09-06 16:15:08
使用FlatFileItemReader读取csv文件时,有一列映射类型为Int,但该列在csv文件中为空(eg:.6321517,Jack, 1,,最后两列为空)。java.lang.NumberFormatException: Unparseable number解析文件时抛出异常( )数据集CUSTR_NBR,SUR_NAME,CHECK_FLAG,RESN_CODE6321517,Jack,1,,首先解析第一行数据(CUSTR_NBR,SUR_NAME,CHECK_FLAG,RESN_CODE),所以我设置.SetLinesToSkip(1). 但如果解析出空值,对应的“CHECK_FLAG”和“RESN_CODE”就无法正常执行。我相信有相应的配置项。我查看了springbatch的文档,没有找到相关的配置项。csvItemReader    @Bean    @StepScope    public FlatFileItemReader<InfoDTO> csvItemReader() {        FlatFileItemReader<InfoDTO> csvItemReader = new FlatFileItemReader<>();        csvItemReader.setResource(new ClassPathResource("data/charge-off.csv"));        csvItemReader.setLinesToSkip(1);        DelimitedLineTokenizer tokenizer=new DelimitedLineTokenizer();        String[] tokens = new String[]{"CUSTR_NBR","SUR_NAME","CHECK_FLAG","RESN_CODE","EMPNO"};        tokenizer.setNames(tokens);        DefaultLineMapper<InfoDTO> lineMapper=new DefaultLineMapper<InfoDTO>();        lineMapper.setLineTokenizer(tokenizer);        lineMapper.setFieldSetMapper(new InfoFileMapper());        lineMapper.afterPropertiesSet();        csvItemReader.setLineMapper(lineMapper);        return csvItemReader;    }映射器    public class InfoFileMapper implements FieldSetMapper<ChargeOffBatchDTO> {        @Override        public InfoDTO mapFieldSet(FieldSet fieldSet) throws BindException {            if(fieldSet == null){                return null;            }            return new InfoDTO(                fieldSet.readString("CUSTR_NBR"),                fieldSet.readString("SUR_NAME"),                fieldSet.readString("CHECK_FLAG"),                fieldSet.readInt("RESN_CODE"),                fieldSet.readInt("EMPNO")            );        }    }我需要将空列映射为0值,如何配置?
查看完整描述

2 回答

?
小怪兽爱吃肉

TA贡献1852条经验 获得超1个赞

我没有使用过 Spring Batch,但查看FieldSet Interface 规范,似乎有一些替代方法可以实现您想要的目标。

然而, Spring Batch 参考确实提到了一些容错能力,特别是当值不存在时抛出异常。为了禁用此功能,您需要将 strict 设置为false

tokenizer.setStrict(false);

否则,您可以简单地尝试一些旧的时尚替代方案,例如不要尝试将值直接读入 an int,只需将其读入 String ,然后在将其转换为 String 之前验证该 Stringint

String empNo = fieldSet.readString("EMPNO");

if ((empNo == null) || (empNo.equals(""))) {

  empNo = "0";

}

int i = Integer.valueOf(empNo);

如果字段不为空且不是字符串,您可能仍然会得到一个java.lang.NumberFormatException,所以就我个人而言,我会通过处理异常来解决问题:


int myEmp = 0;

try {

  myEmp = fieldSet.readInt("EMPNO");

} catch (NumberFormatException nfe) {

  myEmp = 0;

}

也许不是那么雄辩,但它会起作用并达到目的。


查看完整回答
反对 回复 2023-09-06
?
慕标琳琳

TA贡献1830条经验 获得超9个赞

您可以创建自己的行映射器实现,并检查子字符串是否为空,并将其替换为零,然后向前传递该行。



查看完整回答
反对 回复 2023-09-06
  • 2 回答
  • 0 关注
  • 62 浏览

添加回答

举报

0/150
提交
取消
意见反馈 帮助中心 APP下载
官方微信