【问题标题】:Is there any better way to optimize code in setting parameters using 'ParameterizedPreparedStatementSetter'?有没有更好的方法来优化使用“ParameterizedPreparedStatementSetter”设置参数的代码?
【发布时间】:2020-05-25 05:29:40
【问题描述】:

其实我用的是JDBCTemplate,它可以使用ParameterizedPreparedStatementSetter对象批量插入。

但是,当查询的参数很多时,在查询中设置参数是很不方便的。
在我的例子中,实际上,它有 44 个参数。 这是我的代码。

jdbcTemplate.batchUpdate(query.toString(), batchArgs, listSize,
            new ParameterizedPreparedStatementSetter<DocUsageDTO>() {
                @Override
                public void setValues(PreparedStatement ps, DocUsageDTO arg) throws SQLException {
                    ps.setString(1, arg.getClientIp());
                    ps.setInt(2, arg.getClientOs());
                    ps.setString(3, arg.getClientOsVersion());
                    ps.setString(4, arg.getContentCode());
                    ps.setString(5, arg.getContentCreateTime());
                    ps.setString(6, arg.getContentName());
                    ps.setString(7, arg.getCurrentContentName());
                    ps.setString(8, arg.getDeptCode());
                    ps.setString(9, arg.getDeptName());
                    ps.setString(10, arg.getDomainCode());
                    ps.setString(11, arg.getEtc1());
                    ps.setString(12, arg.getEtc2());
                    ps.setString(13, arg.getEtc3());
                    ps.setString(14, arg.getEtc4());
                    ps.setString(15, arg.getEtc5());
                    ps.setString(16, arg.getFileSyncId());
                    ps.setString(17, arg.getFileSyncManagerCode());
                    ps.setString(18, arg.getFileSyncManagerName());
                    ps.setString(19, arg.getFileSyncRevisionNo());
                    ps.setString(20, arg.getFileSyncTagCode());
                    ps.setString(21, arg.getFileSyncTagName());
                    ps.setInt(22, arg.getLocationContext());
                    ps.setString(23, arg.getLogDate());
                    ps.setInt(24, arg.getLogType());
                    ps.setString(25, arg.getOwnerCode());
                    ps.setString(26, arg.getOwnerDeptCode());
                    ps.setString(27, arg.getOwnerDeptName());
                    ps.setString(28, arg.getOwnerName());
                    ps.setString(29, arg.getPositionCode());
                    ps.setString(30, arg.getPositionName());
                    ps.setString(31, arg.getProcessCode());
                    ps.setString(32, arg.getProcessName());
                    ps.setInt(33, arg.getProductType());
                    ps.setInt(34, arg.getPurpose());
                    ps.setInt(35, arg.getPurposeFailReason());
                    ps.setInt(36, arg.getPurposeStatus());
                    ps.setString(37, arg.getSecLevelCode());
                    ps.setString(38, arg.getSecLevelName());
                    ps.setString(39, arg.getUserCode());
                    ps.setString(40, arg.getUserName());
                    ps.setString(41, arg.getWriterCode());
                    ps.setString(42, arg.getWriterDeptCode());
                    ps.setString(43, arg.getWriterDeptName());
                    ps.setString(44, arg.getWriterName());
                }
            });

有没有更好的方法来优化使用ParameterizedPreparedStatementSetter设置参数的代码?

【问题讨论】:

    标签: java jdbctemplate


    【解决方案1】:

    您的问题不是ParameterizedPreparedStatementSetter,而是您的查询有太多参数,以至于任何代码看起来都很庞大。

    您可以尝试NamedParameterJdbcTemplate 在映射中提供参数,但随后您会以某种方式将这 44 个参数放入映射中,这可能仍需要等量的代码。

    您可以将当前的 StatementSetter 变成一个真正的类(而不是现在的匿名类),然后它至少会被封装并且看不见。毕竟只是外观问题,代码本身并没有什么问题。这会让你的服务类看起来更干净,像

    jdbcTemplate.batchUpdate(query.toString(), batchArgs, listSize, new DocUsageDTOSetter());
    

    实际上,您不一定需要NamedParameterJdbcTemplate 的映射,因为它可以使用bean source。但是,这需要参数名称与属性相匹配。这意味着INSERT INTO FOO(bar, baz) VALUES (?, ?) 变为INSERT INTO FOO(bar, baz) VALUES (:myBeanProperty1, :myBeanProperty2),您必须包装每个DTO。因此,您会将(源代码)角色移动到不同的位置,并添加一些额外的对象创建。

    【讨论】:

    • 您的意思是,如果不手动设置参数,就无法避免看起来更干净。我很感激!
    • @임석호 不是真的。 JdbcTemplate 没有非常复杂的参数机制。虽然如果你真的想要,你可以试试NamedParameterJdbcTemplateBeanPropertySqlSource。我会用一个例子来编辑答案。
    【解决方案2】:

    您可以使用命名参数语句而不是像这样手动分配每个参数以提高可读性:

    Connection con=getConnection();
    String query="select * from my_table where name=:name or 
    docUsageDTO =:docUsageDTO ";
    NamedParameterStatement p=new NamedParameterStatement(con, query);
    p.setString("name", "bob");
    p.setString("docUsageDTO", arg); // this just expects all paramters as string ! Didn't want to copy and edit your lengthy code
    ResultSet rs=p.executeQuery();
    

    这样,也许您可​​以创建通用方法来设置参数,方法是通过传递参数名称和循环传递的值或可以减少代码的方法。

    否则,如果您想减少代码但不介意添加繁重的库,那么使用 Hibernate 可以减轻您的负担。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2020-03-14
      • 2023-04-11
      • 1970-01-01
      相关资源
      最近更新 更多