【问题标题】:Java Update PreparedStatementJava 更新 PreparedStatement
【发布时间】:2016-07-11 07:05:12
【问题描述】:

我正在尝试提出一个更新查询,我可以在我的所有应用程序中使用它来更新表(库存)。这是我到目前为止所拥有的:

public void updateInventory(Inventory inventory){
    PreparedStatement ps=null; 
    try {
        String query =  
            "UPDATE "+TableName.INVENTORY +" "+
            "SET quantity=IFNULL(?, quantity), full_stock=IFNULL(?, full_stock), reorder_level=IFNULL(?, reorder_level), selling_price=IFNULL(?, selling_price), delete_status=IFNULL(?, delete_status), product_id=IFNULL(?, product_id) "+
            "WHERE id = ? OR product_id=IFNULL(?, product_id) ";
        connection  = hikariDS.getConnection();  
        ps = connection.prepareStatement(query);
        ps.setFloat(1,inventory.getQuantity());
        ps.setFloat(2,inventory.getFullStock());
        ps.setFloat(3,inventory.getReorderLevel());
        ps.setFloat(4,inventory.getPrice());
        ps.setInt(5, inventory.getDeleteStatus());
        ps.setInt(6, inventory.getProdId());
        ps.setInt(7, inventory.getId());
        ps.setInt(8, inventory.getProdId());
        ps.executeUpdate();
    } catch(SQLException e){ e.printStackTrace();}
    finally{
        if( connection != null ){
            try {connection.close();} 
            catch (SQLException ex) {logger.log(Level.SEVERE, null, ex);}
        }
        if( ps != null){
            try { ps.close();} 
            catch (SQLException ex) { logger.log(Level.SEVERE, null, ex);}
        }
    }
}

上面的查询应该只在对象中设置了新值的情况下更新列,但如果没有设置,只需使用列中的现有值提供它。

问题是:如果从 Inventory 对象中检索到的值为 null 或 0 值,它不会使用现有值进行更新。

【问题讨论】:

  • Inventory 对象怎么可能是0
  • 不是对象本身,而是属性。例如,我只想更新价格但未设置数量,所以我假设价格属性将包含一个值但数量为零
  • @pippilongstocking:您提供的链接是我正在尝试做的,但在我的情况下适用于所有列。问题是如果属性为 0,仍然需要更新属性值而不是列值
  • 尝试使用 JPA 并为您的记录创建实体对象 - 您更希望能够使用 JPA 干净地控制这种类型的动态更新。

标签: java mysql prepared-statement


【解决方案1】:

我假设您的 java 端值(inventory)可能为空,并且您希望为每种可能的值组合使用一段代码。

SQL 看起来不错,但要获取 IFNULL(NULL, ...),假设您的 getter 返回一个 Object 包装器,例如:

Float getQuantity()

那你需要打电话

ps.setObject(1, inventory.getQuantity());

顺便说一句,java 端的BigDecimal 和SQL 模式端的DECIMAL 是更好的选择。对于浮点数的舍入误差。这将启用:

ps.setBigDecimal(1, inventory.getQuantity());

对于非空 getter,使用 IF():

SET quantity = IF(? = 0.0, quantity, ?),

ps.setDouble(1, inventory.getQuantity());
ps.setDouble(2, inventory.getQuantity());

【讨论】:

    【解决方案2】:

    您没有任何东西可以将值实际设置为提供的参数。

    SET quantity=IFNULL(?, quantity), full_stock=IFNULL(?, full_stock), reorder_level=IFNULL(?, reorder_level), selling_price=IFNULL(?, selling_price), delete_status=IFNULL(?, delete_status), product_id=IFNULL(?, product_id) "+
            "WHERE id = ? OR product_id=IFNULL(?, product_id)
    

    应该是

    SET quantity=IFNULL(?, quantity, ?), ...
    

    等等。当然,这意味着您必须复制每个参数。

    【讨论】:

    • 我加了?作为您建议的 IFNULL 函数的第三个参数,抛出错误java.sql.SQLException: No value specified for parameter 9 作为参数应该只有 8 但您的建议增加了更多? . ..
    猜你喜欢
    • 2017-04-04
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2014-06-27
    • 2021-04-19
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多