
本文详解如何通过修正 sql 条件逻辑,正确按月份和木材型号(如 a-001、a-003)分别汇总立方米(cubic)数据,并在 html 表格中动态渲染结果。
在实际木材加工或仓储管理系统中,常需按月统计不同木材类型的出库/加工量(单位:m³)。你当前遇到的核心问题是:SQL 中误将 cubic 字段用于 IF() 的判断条件,而实际应根据 wood 字段匹配型号,再对 cubic 值求和。原始查询中 SUM(IF(cubic='A-001',1,0)) 本质是在计数(且逻辑错误),而非累加体积值——这导致所有分类列显示为 0.0 m³,仅 SUM(cubic) 正确。
✅ 正确做法是:使用 SUM(IF(wood = 'A-001', cubic, 0)) —— 即当 wood 字段匹配特定型号时,取其对应的 cubic 数值参与求和;否则计入 0。同时注意:
- MySQL 中小数分隔符为英文句点(.),但你的示例数据使用了逗号(,),请确保数据库中 cubic 列为 DECIMAL 或 FLOAT 类型,且数据已规范存储(如 0.25 而非 0,25),否则会导致隐式转换失败或求和异常;
- MONTH(date) 仅返回月份数字(1–12),若需显示“2月”等中文名称,可在 PHP 中映射处理;
- WHERE machine='mebor2' 与示例数据中的 mebor1 不一致,请根据实际需求调整过滤条件。
以下是修正后的完整 PHP + MySQL 实现代码(含健壮性增强):
= DATE_SUB(NOW(), INTERVAL 12 MONTH) -- 可选:限制近一年数据 GROUP BY month ORDER BY month ASC"; $result_list = mysqli_query($conn, $sql_list); if (!$result_list) { echo " 月份 Nyár Tölgy VTölgy Cser 合计 "; } elseif (mysqli_num_rows($result_list) === 0) { echo " 查询失败:" . mysqli_error($conn) . " "; } else { while ($row = mysqli_fetch_assoc($result_list)) { // 将数字月份转为中文(可选) $monthName = ['1月','2月','3月','4月','5月','6月', '7月','8月','9月','10月','11月','12月'][$row['month'] - 1] ?? $row['month'] . '月'; ?> 暂无数据 = htmlspecialchars($monthName) ?> = number_format($row['sum_nyar'], 2, '.', '') ?> m³ = number_format($row['sum_tolgy'], 2, '.', '') ?> m³ = number_format($row['sum_vtolgy'], 2, '.', '') ?> m³ = number_format($row['sum_cser'], 2, '.', '') ?> m³ = number_format($row['sum_full'], 2, '.', '') ?> m³
? 关键改进说明:
立即学习“PHP免费学习笔记(深入)”;
- 使用 COALESCE(..., 0) 防止 NULL 值在前端显示为空白;
- number_format($val, 2, '.', '') 统一使用英文小数点,避免 locale 导致格式混乱;
- 添加 htmlspecialchars() 防止 XSS(尤其当字段内容可能含用户输入时);
- 增加错误处理与空数据提示,提升生产环境鲁棒性;
- ORDER BY month ASC 确保月份升序排列,便于阅读。
? 进阶建议:
若木材类型较多或动态变化,可考虑用 CASE WHEN 或预聚合视图替代硬编码 IF;更灵活的方案是先查出所有唯一 wood 值,再动态构建列名与 SQL,结合 PDO 的预处理语句实现完全动态报表。











