You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Java从MySQL按日期范围查询数据缺失最后一天的问题

日期区间查询遗漏数据的问题排查与解决

我来帮你搞定这个问题——你遇到的「查询区间最后一天数据加载不出来」的情况,本质是时间精度匹配的问题,咱们一步步拆解解决:

问题根源

当你通过jDateChooser获取日期并转成Timestamp时,默认生成的是该日期的00:00:00.000时刻。而MySQL的BETWEEN是包含两端值的,但如果你的MsarefDate字段是带具体时间的(比如2020-01-31 09:15:00),那么它会大于2020-01-31 00:00:00,自然不会被BETWEEN '2020-01-01 00:00:00' AND '2020-01-31 00:00:00'选中。

同理,选到2020-02-01时,只有2020-02-01 00:00:00及之前的记录会被包含,也就是1月31日23:59:59之前的数据,2月1日的所有记录都不在范围内。

两种可行解决方案

方案1:把结束时间往后推一天(推荐,不影响索引)

把结束日期的时间调整为次日00:00:00,这样原结束日期的所有时间点的记录都会被包含在< 次日0点的范围内:

// 处理起始日期
java.util.Date startDate = jDateChooser5.getDate();
java.sql.Timestamp timestamp = new java.sql.Timestamp(startDate.getTime());

// 处理结束日期:加一天
java.util.Date endDate = jDateChooser6.getDate();
Calendar cal = Calendar.getInstance();
cal.setTime(endDate);
cal.add(Calendar.DATE, 1); // 往后推一天
java.sql.Timestamp timestamp2 = new java.sql.Timestamp(cal.getTimeInMillis());

对应的SQL改成用>=和<(比BETWEEN更清晰):

SELECT sum(`msareffishmarket`.`Amount`) 
FROM `manfz`.`msareffishmarket` 
WHERE `msareffishmarket`.`place` = 'محل الأسماك' 
  AND `msareffishmarket`.`MsarefDate` >= ? 
  AND `msareffishmarket`.`MsarefDate` < ? 
GROUP BY DATE(`msareffishmarket`.`MsarefDate`)

方案2:直接比较日期部分(简单但可能影响性能)

如果你的MsarefDate字段是datetime/timestamp类型,可以直接提取日期部分进行比较,这样就不用考虑时间:

SELECT sum(`msareffishmarket`.`Amount`) 
FROM `manfz`.`msareffishmarket` 
WHERE `msareffishmarket`.`place` = 'محل الأسماك' 
  AND DATE(`msareffishmarket`.`MsarefDate`) BETWEEN ? AND ? 
GROUP BY DATE(`msareffishmarket`.`MsarefDate`)

⚠️ 注意:这种写法会让MsarefDate上的索引失效,如果数据量很大,查询速度会变慢,所以优先选方案1。

重要优化:避免SQL注入!

你当前的代码直接把Timestamp拼接到SQL字符串里,这存在严重的SQL注入风险!一定要用PreparedStatement的参数绑定来传递变量,这也是Java操作数据库的最佳实践。

修改后的完整代码示例:

try {
    // 处理起始日期
    java.util.Date startDate = jDateChooser5.getDate();
    java.sql.Timestamp timestamp = new java.sql.Timestamp(startDate.getTime());

    // 处理结束日期:加一天
    java.util.Date endDate = jDateChooser6.getDate();
    Calendar cal = Calendar.getInstance();
    cal.setTime(endDate);
    cal.add(Calendar.DATE, 1);
    java.sql.Timestamp timestamp2 = new java.sql.Timestamp(cal.getTimeInMillis());

    // 预编译SQL,用?作为占位符
    String sql2 = "SELECT sum(`msareffishmarket`.`Amount`) " +
                  "FROM `manfz`.`msareffishmarket` " +
                  "WHERE `msareffishmarket`.`place` = 'محل الأسماك' " +
                  "  AND `msareffishmarket`.`MsarefDate` >= ? " +
                  "  AND `msareffishmarket`.`MsarefDate` < ? " +
                  "GROUP BY DATE(`msareffishmarket`.`MsarefDate`)";

    stm2 = conn.prepareStatement(sql2);
    // 绑定参数,位置从1开始
    stm2.setTimestamp(1, timestamp);
    stm2.setTimestamp(2, timestamp2);
    rs2 = stm2.executeQuery();

    // 加载数据到表格
    jTable3.setModel(DbUtils.resultSetToTableModel(rs2));
} catch (SQLException ex) {
    // 异常处理,给用户友好提示
    ex.printStackTrace();
    JOptionPane.showMessageDialog(this, "查询出错:" + ex.getMessage());
} finally {
    // 关闭资源,避免内存泄漏
    try {
        if (rs2 != null) rs2.close();
        if (stm2 != null) stm2.close();
    } catch (SQLException ex) {
        ex.printStackTrace();
    }
}

这样修改后,不仅能正确加载结束日期的所有数据,还能避免SQL注入的安全问题,同时保证查询性能。

内容的提问来源于stack exchange,提问作者Mahmoud Hassan Mohamed Hassan

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.06 14:52:50