正确使用sum()函数关联多表实现金额求和的问题
问题分析与修复方案
你遇到的计算错误,核心问题出在Table1和Table2的关联逻辑上——你之前只通过nameID关联两个表,没有匹配entryDate,这会导致同用户但不同日期的记录被错误地配对相加(比如Table1里5月1日的nameID=2记录,会和Table2里5月6日的nameID=2记录强行相加),完全不符合“对应日期对应列相加”的需求。
你的表结构与初始化数据
-- 创建表与插入测试数据 CREATE TABLE `Name` ( `id` INTEGER PRIMARY KEY AUTOINCREMENT, `name` TEXT ); INSERT INTO `Name` VALUES(1,'test1'); INSERT INTO `Name` VALUES(2,'test2'); CREATE TABLE "Table1" ( `id` INTEGER NOT NULL PRIMARY KEY AUTOINCREMENT, `nameID` INTEGER, `amnt1` INTEGER, `amnt2` INTEGER, `amnt3` INTEGER, `amnt4` INTEGER, `amnt5` INTEGER, `amnt6` INTEGER, `entryDate` TEXT ); INSERT INTO Table1 VALUES(NULL,1,1,1,1,1,1,1,'2018-04-01'); INSERT INTO Table1 VALUES(NULL,2,1,1,1,1,1,1,'2018-05-01'); INSERT INTO Table1 VALUES(NULL,1,1,1,1,1,1,1,'2018-05-06'); CREATE TABLE "Table2" ( `id` INTEGER NOT NULL PRIMARY KEY AUTOINCREMENT, `nameID` INTEGER, `amnt1` INTEGER, `amnt2` INTEGER, `amnt3` INTEGER, `amnt4` INTEGER, `amnt5` INTEGER, `amnt6` INTEGER, `entryDate` TEXT ); INSERT INTO Table2 VALUES(NULL,1,1,1,1,1,1,1,'2018-04-02'); INSERT INTO Table2 VALUES(NULL,1,1,1,1,1,1,1,'2018-05-05'); INSERT INTO Table2 VALUES(NULL,2,2,2,2,2,2,1,'2018-05-06'); CREATE TABLE "Table3" ( `id` INTEGER NOT NULL PRIMARY KEY AUTOINCREMENT, `nameID` INTEGER, `amnt1` INTEGER, `amnt2` INTEGER, `amnt3` INTEGER, `amnt4` INTEGER, `amnt5` INTEGER, `amnt6` INTEGER, `entryDate` TEXT ); INSERT INTO Table3 VALUES(NULL,1,1,1,1,1,1,1,'2018-04-02'); INSERT INTO Table3 VALUES(NULL,1,1,1,1,1,1,1,'2018-05-05');
修复后的查询语句
我们需要确保同nameID、同entryDate的Table1和Table2记录才相加,同时处理某一天只有其中一个表有记录的情况(用COALESCE把NULL值转为0,避免相加结果为NULL),再把这个结果和Table3的指定日期记录合并后求和:
SELECT SUM(amnt1) AS total_amnt1, SUM(amnt2) AS total_amnt2, SUM(amnt3) AS total_amnt3, SUM(amnt4) AS total_amnt4, SUM(amnt5) AS total_amnt5, SUM(amnt6) AS total_amnt6 FROM ( -- 处理Table1和Table2的同日期同用户相加 SELECT COALESCE(t1.nameID, t2.nameID) AS nameID, COALESCE(t1.amnt1, 0) + COALESCE(t2.amnt1, 0) AS amnt1, COALESCE(t1.amnt2, 0) + COALESCE(t2.amnt2, 0) AS amnt2, COALESCE(t1.amnt3, 0) + COALESCE(t2.amnt3, 0) AS amnt3, COALESCE(t1.amnt4, 0) + COALESCE(t2.amnt4, 0) AS amnt4, COALESCE(t1.amnt5, 0) + COALESCE(t2.amnt5, 0) AS amnt5, COALESCE(t1.amnt6, 0) + COALESCE(t2.amnt6, 0) AS amnt6, COALESCE(t1.entryDate, t2.entryDate) AS entryDate FROM Table1 t1 FULL OUTER JOIN Table2 t2 ON t1.nameID = t2.nameID AND t1.entryDate = t2.entryDate WHERE COALESCE(t1.entryDate, t2.entryDate) BETWEEN '2018-05-01' AND '2018-05-20' UNION ALL -- 加入Table3的指定日期记录 SELECT nameID, amnt1, amnt2, amnt3, amnt4, amnt5, amnt6, entryDate FROM Table3 WHERE entryDate BETWEEN '2018-05-01' AND '2018-05-20' ) combined_data;
关键修改点说明
- 关联条件新增entryDate:确保只有同一天、同一用户的记录才会被配对相加,彻底避免跨日期的错误关联。
- 使用COALESCE处理NULL:如果某一天只有Table1或Table2有记录,另一个表的字段会是NULL,
COALESCE(字段, 0)会把NULL转为0,保证相加结果不为空且正确。 - FULL OUTER JOIN:确保不会漏掉只有Table1或只有Table2有记录的日期,覆盖所有可能的场景。
内容的提问来源于stack exchange,提问作者u4547878
相关产品推荐
相关产品推荐

