JDBC / Resultset错误

时间:2012-01-02 10:52:08

标签: java mysql jdbc limit max

我在Java中的mysql查询总是在某个位置停止(即冻结并且不继续),即543,858;即使表包含约。 2,000,000个条目。我通过记录当前的结果获取来检查这一点。 它是可重复的,每次都在同一个位置发生。

"SELECT abc from bcd WHERE DATEDIFF(CURDATE(), timestamp) <= '"+days+"'");

另外:肯定 是一个Java错误,我刚刚在Navicat(50s运行时)中尝试了这个语句。

在日志告诉我它现在正在添加位置543,858的结果后,查询似乎冻结了。

try {
    ...
    ResultSet res = new ResultSet();
    PreparedStatement stmt = new PreparedStatement(); // prepare statmenet etc.
    stmt.setFetchSize(Integer.MIN_VALUE);
    res = stmt.executeQuery();
    ...
    System.out.println(res.getStatement());
    ...
    while (res.next())
        treeSet.add(res.getString("userid"));

} catch (Exception e) {
     e.printStackTrace();
}

编辑:我们能够找出问题所在。这种方法很好,返回的结果(500,000而不是2,000,000)也是正确的(在错误的数据库中查找以验证数量);问题是,使用上面发布的结果的下一个方法调用实际上是永远的,但没有记录实现。所以我被错过的控制台日志所迷惑。

非常感谢!

3 个答案:

答案 0 :(得分:1)

我认为在处理了50万条记录后你可能会耗尽内存。尝试使用命令行选项-Xmx等分配更多内存。有关命令行选项的详细信息,请参阅here

答案 1 :(得分:1)

在mysql中使用流式ResultSet,您必须指定更多参数,而不仅仅是fetchSize。

尝试:

stmt = conn.createStatement('select ...', java.sql.ResultSet.TYPE_FORWARD_ONLY, java.sql.ResultSet.CONCUR_READ_ONLY);
stmt.setFetchSize(Integer.MIN_VALUE);

看看是否有效。

ResultSet部分中的documented

奇怪的是它没有抛出异常,但这是我唯一的嫌疑人。也许它开始垃圾收集/刷新内存到磁盘,它需要花费很多时间才能扔掉它。

答案 2 :(得分:0)

  1. 我会尝试添加到您的查询“LIMIT 543857”然后“LIMIT 543857”,看看会发生什么。
  2. 如果上述方法无效,请使用limit指令和order by。
  3. 我怀疑你的表中存在无效条目,找到它的方法是二进制搜索。