Sql 计数案例返回错误的结果
我正在尝试统计在30分钟内和30分钟以上关闭的订单数量 表结构和示例数据Sql 计数案例返回错误的结果,sql,sql-server,Sql,Sql Server,我正在尝试统计在30分钟内和30分钟以上关闭的订单数量 表结构和示例数据 ORDERID CUSTOMERID ORDERDATE CLOSEDDATE STATUSID --------------------------------------------------------------------------------- 14 1 2018-07-03 11:02:54.000 2018-07-0
ORDERID CUSTOMERID ORDERDATE CLOSEDDATE STATUSID
---------------------------------------------------------------------------------
14 1 2018-07-03 11:02:54.000 2018-07-03 13:15:58.000 CLOSED
15 1 2018-07-03 13:22:42.000 NULL DISPATCHED
16 1 2018-07-03 13:26:04.000 NULL DISPATCHED
17 1 2018-07-03 13:27:57.000 2018-07-03 13:28:28.000 CLOSED
18 1 2018-07-03 17:23:45.000 NULL RECEIVED
查询:
SELECT
OUTLETNAME,
COUNT(ORDERID) AS ORDERSCOUNT,
COUNT(DISTINCT(dbo.VW_SALES_SUM.CUSTOMERID)) AS CUSTOMERCOUNT,
COUNT(CASE WHEN DATEDIFF(mi, dbo.VW_SALES_SUM.ORDERDATE, dbo.VW_SALES_SUM.CLOSEDDATE) < 30 AND dbo.VW_SALES_SUM.STATUSID = 'CLOSED'
THEN 1
ELSE 0
END) [LESS 30 (CLOSED)],
COUNT(CASE WHEN DATEDIFF(mi, dbo.VW_SALES_SUM.ORDERDATE, dbo.VW_SALES_SUM.CLOSEDDATE) > 30 AND dbo.VW_SALES_SUM.STATUSID = 'CLOSED'
THEN 1 ELSE 0
END) [Greater 30 (CLOSED)]
FROM
dbo.VW_SALES_SUM
INNER JOIN
dbo.[OUTLET] ON dbo.VW_SALES_SUM.OUTLETCODE = dbo.[OUTLET].CODE
WHERE
dbo.VW_SALES_SUM.ORDERDATE BETWEEN '7/3/2018 11:00:00 AM' AND '7/4/2018 02:00:00 AM'
GROUP BY
OUTLETNAME, dbo.OUTLET.BRAND
ORDER BY
COUNT(ORDERID) DESC
从输出中我们可以看到,它返回了错误的已关闭订单计数,它总是返回订单总数
输出应如下所示:
OUTLETNAME ORDERSCOUNT CUSTOMERCOUNT LESS 30 (CLOSED) Greater 30 (CLOSED)
-------------------------------------------------------------------------
shop1 5 1 0 2
使用SUM代替count
SELECT
OUTLETNAME,
COUNT(ORDERID) AS ORDERSCOUNT,
COUNT(distinct(dbo.VW_SALES_SUM.CUSTOMERID)) as CUSTOMERCOUNT,
SUM(case when DATEDIFF(mi, dbo.VW_SALES_SUM.ORDERDATE, dbo.VW_SALES_SUM.CLOSEDDATE) < 30 and dbo.VW_SALES_SUM.STATUSID='CLOSED' then 1 else 0 end) [LESS 30 (CLOSED)],
SUM(case when DATEDIFF(mi, dbo.VW_SALES_SUM.ORDERDATE, dbo.VW_SALES_SUM.CLOSEDDATE) > 30 and dbo.VW_SALES_SUM.STATUSID='CLOSED' then 1 else 0 end) [Greater 30 (CLOSED)]
FROM
dbo.VW_SALES_SUM
INNER JOIN
dbo.[OUTLET] ON dbo.VW_SALES_SUM.OUTLETCODE = dbo.[OUTLET].CODE
WHERE
dbo.VW_SALES_SUM.ORDERDATE BETWEEN '7/3/2018 11:00:00 AM' AND '7/4/2018 02:00:00 AM'
GROUP BY
OUTLETNAME, dbo.OUTLET.BRAND
ORDER BY
COUNT(ORDERID) DESC
选择
OUTLETNAME,
将(ORDERID)计数为OrderScont,
将(不同的(dbo.VW\u SALES\u SUM.CUSTOMERID))计数为CUSTOMERCOUNT,
总和(当DATEDIFF(mi,dbo.VW_SALES_SUM.ORDERDATE,dbo.VW_SALES_SUM.CLOSEDDATE)小于30且dbo.VW_SALES_SUM.STATUSID='CLOSED'则为1,否则为0结束)[小于30(CLOSED)],
总和(DATEDIFF(mi,dbo.VW_SALES_SUM.ORDERDATE,dbo.VW_SALES_SUM.CLOSEDDATE)大于30且dbo.VW_SALES_SUM.STATUSID='CLOSED'则1为0结束时的情况)[大于30(已关闭)]
从…起
dbo.VW\u销售金额
内连接
dbo.VW\u SALES\u SUM.OUTLETCODE=dbo[OUTLET].CODE上的dbo[OUTLET]
哪里
dbo.VW_销售_SUM.ORDERDATE介于“2018年7月3日上午11:00:00”和“2018年7月4日上午02:00:00”之间
分组
OUTLETNAME,dbo.OUTLET.BRAND
订购人
计数(订单ID)描述
而不是同时计算1和0。你所要做的就是不要把两者都计算在内
问题是,按值计数不计算空值。但如果只返回值0或1,则计数的行为与计数(*)没有区别。因为它不返回任何NULL,所以计数可以忽略 所以只要去掉那些
ELSE 0
就可以了
顺便说一句,使用别名可以缩短SQL
SELECT
OUTLETNAME,
COUNT(ORDERID) AS ORDERSCOUNT,
COUNT(DISTINCT(s.CUSTOMERID)) AS CUSTOMERCOUNT,
COUNT(CASE
WHEN DATEDIFF(mi, s.ORDERDATE, s.CLOSEDDATE) < 30 AND s.STATUSID = 'CLOSED'
THEN 1
END) [LESS 30 (CLOSED)],
COUNT(CASE
WHEN DATEDIFF(mi, s.ORDERDATE, s.CLOSEDDATE) > 30 AND s.STATUSID = 'CLOSED'
THEN 1
END) [Greater 30 (CLOSED)]
FROM dbo.VW_SALES_SUM s
JOIN dbo.[OUTLET] o ON o.CODE = s.OUTLETCODE
WHERE
s.ORDERDATE BETWEEN '7/3/2018 11:00:00 AM' AND '7/4/2018 02:00:00 AM'
GROUP BY OUTLETNAME, o.BRAND
ORDER BY COUNT(ORDERID) DESC
0
和1
都是非空的,因此生成其中一个的表达式将对每行执行一次COUNT
。您是否打算改为SUM()
?我使用了相同的SUM概念,但在这种情况下,我需要计算此列表中有多少项-0,1,0,0,1?五个,对吗?这就是COUNT
给你的。如果您想将这些数字相加,请使用SUM
(或从案例中取出ELSE
子句,让它在这种情况下生成NULL
,这样就不会被计算在内)改为SUM而不是count谢谢Damien的帮助我搜索了这么长时间为什么我的查询出现错误计数。。然后删除这条简单的行ELSE 0
。。工作!
SELECT
OUTLETNAME,
COUNT(ORDERID) AS ORDERSCOUNT,
COUNT(DISTINCT(s.CUSTOMERID)) AS CUSTOMERCOUNT,
COUNT(CASE
WHEN DATEDIFF(mi, s.ORDERDATE, s.CLOSEDDATE) < 30 AND s.STATUSID = 'CLOSED'
THEN 1
END) [LESS 30 (CLOSED)],
COUNT(CASE
WHEN DATEDIFF(mi, s.ORDERDATE, s.CLOSEDDATE) > 30 AND s.STATUSID = 'CLOSED'
THEN 1
END) [Greater 30 (CLOSED)]
FROM dbo.VW_SALES_SUM s
JOIN dbo.[OUTLET] o ON o.CODE = s.OUTLETCODE
WHERE
s.ORDERDATE BETWEEN '7/3/2018 11:00:00 AM' AND '7/4/2018 02:00:00 AM'
GROUP BY OUTLETNAME, o.BRAND
ORDER BY COUNT(ORDERID) DESC
SELECT COUNT(DISTINCT CASE WHEN col1='bar' then col2 END) AS Bars FROM Foo;