【问题标题】:(JAVA/SQL) ResultSet only retrieving one row from MySQL when it should retrieve more(JAVA/SQL) ResultSet 只从 MySQL 中检索一行,而它应该检索更多行
【发布时间】:2015-09-13 22:16:33
【问题描述】:

我在我的 Java servlet 中从 MySQL 数据库中检索数据时遇到了一点问题。作为参考,我的 Web 应用程序的构造类似于库 - 您可以签出项目,然后将它们重新签入。

当您第一次点击“结帐”时,您的请求会发送给管理员,让我们称此人为图书管理员,他必须批准或拒绝您的请求。假设我登录,选择一些项目,然后点击“结帐”。以下是发生的事情:

  1. 商品被添加到我的“购物车”
  2. 在数据库的项目主列表中,每个项目都有一个名为STATUSVARCHAR,用于标识该项目是否为"In Stock"。对于我选择的每个项目,该变量都会更改为与我的用户帐户关联的唯一标识符。
  3. 我的请求被添加到名为requests_list 的表中

审批、通用签到等工作正常。效果不佳的是单击“不赞成”。以下是应该发生的事情:

  1. 请求已从requests_list 中删除
  2. 请求者的“购物车”项目被截断
  3. 项目本身被声明为"In Stock"

这是发生了什么:

  1. 请求已从requests_list 中删除
  2. 请求者的“购物车”项目被截断
  3. 只有购物车中的第一件商品才能重新签入

这是我目前正在使用的代码:

stmt.execute("DELETE FROM requests_list WHERE UNIQUE_ID = '"
                        + selected_ID + "'"); // this seems to work

stmt.execute("TRUNCATE TABLE checkout_" + selected_ID); // also seems to work

ResultSet all_gear = stmt
                        .executeQuery("SELECT * FROM gear_master_list");

while (all_gear.next()) {
    if (all_gear.getString(5).equals(selected_ID)) {
        stmt.execute("UPDATE gear_master_list SET STATUS = 'In Stock' WHERE ID_NUM = "
                                + all_gear.getInt(6));
    }
}

all_gear.close();

一些注释,解释一些变量:

  • selected_ID - 图书管理员单击下拉菜单以访问已提出请求的用户列表。在他或她选择一个之后,该用户的唯一标识符变为selected_ID
  • checkout_selected_ID - 您的“购物车”是数据库中的一个表。此表以您的唯一 ID 命名,因此如果我的唯一 ID 是兔子,我的表将是 checkout_bunnies
  • stmt 和它从中提取 StatementConnection 都是有效且有效的
  • gear_master_list 是所有装备的表格,all_gear.getInt(6) 引用了每个装备的唯一库存编号,all_gear.getString(5) 是我提到的STATUS 变量

我尝试过以不同的方式执行此操作,这样代码会遍历购物车中的所有商品,更新状态,然后截断表格。这也不起作用 - 更新状态仍然很挑剔,而且表格不会截断。

TL;DR: 我的ResultSet 只让我从我的表中获得一行(我认为),即使我使用的是while 循环并且有不止一行。这是怎么回事?有没有更好、更有效的方法来做到这一点?

【问题讨论】:

  • 您是否调试过您的结果集包含所有项目,还分享您的错误跟踪..

标签: java mysql sql-server openshift resultset


【解决方案1】:

这可能是一个并发修改问题 - 您的第一个查询保持打开数据库上的一个游标,并且在循环该游标时您正在对同一数据执行更新,所有这些都在同一个事务中。

你能试试这个吗?

    stmt.execute("DELETE FROM requests_list WHERE UNIQUE_ID = '"
            + selected_ID + "'"); // this seems to work

    stmt.execute("TRUNCATE TABLE checkout_" + selected_ID); // also seems to
                                                            // work

    ResultSet all_gear = stmt
            .executeQuery("SELECT * FROM gear_master_list");

    List<String> gear_items = new ArrayList<>();
    while (all_gear.next()) {
        gear_items.add(all_gear.getString(5));
    }
    all_gear.close();

    for (String gear_item: gear_items){
        if (all_gear.getString(5).equals(selected_ID)) {
            stmt.execute("UPDATE gear_master_list SET STATUS = 'In Stock' WHERE ID_NUM = "
                    + all_gear.getInt(6));
        }
    }

    stmt.close();

【讨论】:

  • 非常感谢!通过一些修改,这解决了我的问题。我欠你的!
  • 谢谢 :) 希望你能把它转发给其他 SO-ers!
【解决方案2】:

非常感谢休在这个问题上的大力帮助 - 他的回答是正确的。我只需要进行一些修改以帮助他的响应适合我的代码。

如果其他人遇到这个问题,休是对的,这是一个并发修改问题。然而,他的回复中有一个小错误(在调用某些语句之前 ResultSet 被关闭),所以我想我会发布我修改过的代码,以防万一它对任何人都有帮助:

stmt.execute("DELETE FROM requests_list WHERE UNIQUE_ID = '" + selected_ID + "'"); // this seems to work

stmt.execute("TRUNCATE TABLE checkout_" + selected_ID); // also seems to work

ResultSet all_gear = stmt.executeQuery("SELECT * FROM gear_master_list");

ArrayList<Object[]> gear_items = new ArrayList<Object[]>();
while (all_gear.next()) {
    Object[] added = new Object[2];
    added[0] = all_gear.getString(5);
    added[1] = all_gear.getInt(6);
    gear_items.add(added);
}
all_gear.close();

for (Object[] gear_item : gear_items) {
    if (gear_item[0].equals(selected_ID)) {
        stmt.execute("UPDATE gear_master_list SET STATUS = 'In Stock' WHERE ID_NUM = " + gear_item[1]);
    }
}

stmt.close();

// thanks again to hugh!

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2020-09-06
    • 1970-01-01
    • 2012-06-27
    • 2016-02-15
    • 2023-04-02
    • 1970-01-01
    • 2013-05-28
    相关资源
    最近更新 更多