按日期分组

时间:2017-03-09 17:06:39

标签: sql sql-server

我有两个表,Sales和Calls如下:

**Sales** 
CUST_ID            INT primary key,
CUST_NM            Varchar(40),
Sale_date          Datetime2,
SALES              Money);
CUST_ID CUST_NM           Sale_date               SALES
1          Dom      2015-01-01 15:00:02.3000000   10.00
2          Brian    2015-01-02 15:00:02.3000000   12.00
3          Stu      2015-01-03 15:00:02.3000000   21.00
4          John     2015-01-04 15:00:02.3000000   41.00
5          Jack     2015-01-05 15:00:02.3000000   51.00
6          Jill     2015-01-05 15:00:02.3000000   61.00
7          Steve    2015-01-04 15:00:02.3000000   16.00
8          Stacey   2015-01-03 15:00:02.3000000   19.00
9          Lacey    2015-01-03 15:00:02.3000000   30.00

通话

NAME               Varchar(40),
CALL_DATE          Date,
TOTAL_CALLS        INT


NAME       CALL_DATE    TOTAL_CALLS
Dom        2015-01-01   2
Brian      2015-01-02   4
Stu        2015-01-03   3
John       2015-01-04   5
Jack       2015-01-05   6
Jill       2015-01-05   10
Steve      2015-01-04   8
Stacey     2015-01-03   7
Lacey      2015-01-03   9

我想写一个select语句,它会带来日期,总销售额以及来自销售和通话的总来电次数。

这是我写的,我认为它应该是正确的,但不知怎的,我没有得到正确的输出。

select Calls.CALL_DATE, sum(Sales.SALES) as gross_sale, sum(Calls.TOTAL_CALLS) as gross_total_calls
from Sales
join
Calls 
on convert (date,sales.Sale_date)=calls.CALL_DATE
group by Calls.CALL_DATE
order by Calls.CALL_DATE

我得到的输出是

CALL_DATE   gross_sale   gross_total_calls

2015-01-01  10.00        2
2015-01-02  12.00        4
2015-01-03  210.00       57
2015-01-04  114.00       26
2015-01-05  224.00       32

我哪里错了?

2 个答案:

答案 0 :(得分:1)

您每天都在生成笛卡尔积。您需要在join之前汇总。或者,您可以使用union all和聚合:

执行此操作
select dte, sum(sales) as sales, sum(calls) as total_calls
from ((select cast(s.sale_date as date) as dte, sales, 0 as calls
       from sales s
      ) union all
      (select call_date, 0, total_calls as calls
       from calls c
      )
     ) sc
group by dte
order by dte;

答案 1 :(得分:0)

Gordon使用表变量建议的替代方法来创建可运行的测试脚本。 注意两行额外的数据和FULL OUTER JOIN,它允许返回所有数据。

declare @Sales table (CUST_ID INT primary key, CUST_NM Varchar(40), Sale_date Datetime2,SALES Money);
insert into @Sales (CUST_ID, CUST_NM, Sale_date, SALES)
select 1, 'Dom', '2015-01-01 15:00:02.3000000', 10.00 union
select 2, 'Brian', '2015-01-02 15:00:02.3000000', 12.00 union
select 3, 'Stu', '2015-01-03 15:00:02.3000000', 21.00 union
select 4, 'John', '2015-01-04 15:00:02.3000000', 41.00 union
select 5, 'Jack', '2015-01-05 15:00:02.3000000', 51.00 union
select 6, 'Jill', '2015-01-05 15:00:02.3000000', 61.00 union
select 7, 'Steve', '2015-01-04 15:00:02.3000000', 16.00 union
select 8, 'Stacey', '2015-01-03 15:00:02.3000000', 19.00 union
select 9, 'Lacey', '2015-01-03 15:00:02.3000000', 30.00 union
select 10, 'Tom', '2015-01-07 15:00:02.3000000', 1.00

declare @Calls table (NAME Varchar(40), CALL_DATE Date, TOTAL_CALLS INT)
insert into @Calls (NAME, CALL_DATE, TOTAL_CALLS)
select 'Dom', '2015-01-01', 2 union
select 'Brian', '2015-01-02', 4 union
select 'Stu', '2015-01-03', 3 union
select 'John', '2015-01-04', 5 union
select 'Jack', '2015-01-05', 6 union
select 'Jill', '2015-01-05', 10 union
select 'Steve', '2015-01-04', 8 union
select 'Stacey', '2015-01-03', 7 union
select 'Lacey', '2015-01-03', 9 union
select 'Tom', '2015-01-06', 1

select * from @Sales
select * from @Calls

select ISNULL (a.CALL_DATE, b.CALL_DATE) as CALL_DATE, gross_sale, TOTAL_CALLS
from 
( select convert(date, Sale_date) as CALL_DATE, sum(SALES) as gross_sale
  from @Sales
  group by convert(date, Sale_date)
) a
full outer join
( select CALL_DATE, SUM(TOTAL_CALLS) as TOTAL_CALLS
  from @Calls
  group by CALL_DATE
) b on a.CALL_DATE = b.CALL_DATE
order by a.CALL_DATE