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

使用WITH AS编写SQL月度销售对比查询结果行数异常求助

解决WITH AS查询返回笛卡尔积的问题

你遇到的这个问题很常见——当前查询里用了SELECT * FROM TABLE_CURRENT, TABLE_LAST这种隐式交叉连接,它会把两个CTE的所有行做全组合匹配,所以如果每个CTE各有3行,结果自然就是3×3=9行,也就是你看到的“平方数行数”。

要得到按月度对比的3行数据,核心是让今年的每个月份和去年对应的月份做一对一关联,而不是全组合。这里给你两种修改思路:

方法1:提取月份字段做显式JOIN

修改两个CTE,额外单独提取月份数字,然后用INNER JOIN关联相同的月份,确保每行都是同月份的新老数据对比:

DECLARE @MAX_DATE AS INT 
SET @MAX_DATE = (SELECT DATEPART(MONTH,FECHA) FROM ALBVENTACAB WHERE NUMALBARAN IN (SELECT DISTINCT MAX(NUMALBARAN) FROM ALBVENTACAB)); 
;WITH TABLE_LAST AS ( 
 SELECT DATEPART(MONTH,FECHA) AS MONTH_NUM -- 单独提取月份数字用于关联
 ,CONCAT(DATEPART(MONTH,FECHA),'-',DATEPART(YEAR,FECHA)) as LAST_YEAR_MONTH 
 ,SUM(TOTALNETO) AS LAST_YEAR_VALUE 
 FROM ALBVENTACAB 
 WHERE DATEPART(YEAR,CURRENT_TIMESTAMP) -1 = DATEPART(YEAR,FECHA) AND NUMSERIE LIKE 'A%' AND DATEPART(MONTH,FECHA) <= @MAX_DATE 
 GROUP BY DATEPART(MONTH,FECHA), CONCAT(DATEPART(MONTH,FECHA),'-',DATEPART(YEAR,FECHA)) 
 ) 
 ,TABLE_CURRENT AS( 
 SELECT DATEPART(MONTH,FECHA) AS MONTH_NUM -- 同样提取月份数字
 ,CONCAT(DATEPART(MONTH,FECHA),'-',DATEPART(YEAR,FECHA)) as CURR_YEAR_MONTH 
 ,SUM(TOTALNETO) AS CURR_YEAR_VALUE 
 FROM ALBVENTACAB 
 WHERE DATEPART(YEAR,CURRENT_TIMESTAMP) = DATEPART(YEAR,FECHA) AND NUMSERIE LIKE 'A%' AND DATEPART(MONTH,FECHA) <= @MAX_DATE -- 加上@MAX_DATE和去年保持一致的月份范围
 GROUP BY DATEPART(MONTH,FECHA), CONCAT(DATEPART(MONTH,FECHA),'-',DATEPART(YEAR,FECHA)) 
 ) 
 SELECT 
  TC.CURR_YEAR_MONTH,
  TC.CURR_YEAR_VALUE,
  TL.LAST_YEAR_MONTH,
  TL.LAST_YEAR_VALUE
 FROM TABLE_CURRENT TC
 INNER JOIN TABLE_LAST TL ON TC.MONTH_NUM = TL.MONTH_NUM -- 关联相同月份

方法2:直接拆分日期字符串关联

如果不想修改CTE结构,也可以通过拆分LAST_YEAR_MONTH和CURR_YEAR_MONTH的月份部分来做关联:

-- 前面的CTE部分保持不变
 SELECT 
  TC.CURR_YEAR_MONTH,
  TC.CURR_YEAR_VALUE,
  TL.LAST_YEAR_MONTH,
  TL.LAST_YEAR_VALUE
 FROM TABLE_CURRENT TC
 INNER JOIN TABLE_LAST TL 
 ON LEFT(TC.CURR_YEAR_MONTH, CHARINDEX('-', TC.CURR_YEAR_MONTH)-1) = LEFT(TL.LAST_YEAR_MONTH, CHARINDEX('-', TL.LAST_YEAR_MONTH)-1)

另外提个小建议:你的TABLE_CURRENT里的条件DATEPART(YEAR,CURRENT_TIMESTAMP) <= DATEPART(YEAR,FECHA)可能会包含未来年份的数据(如果表中有),建议改成DATEPART(YEAR,CURRENT_TIMESTAMP) = DATEPART(YEAR,FECHA),同时加上DATEPART(MONTH,FECHA) <= @MAX_DATE,这样今年和去年的月份范围保持一致,避免出现去年没有的月份导致关联不上的情况。

内容的提问来源于stack exchange,提问作者Fawad Jalal

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.05.09 15:32:46