我在SQL Server,Customers,Items和Transactions中有3个表。表Transactions中的C_id和I.id是来自Customers和Items表的外键。我想要一个特定的日期范围来查看所有客户,所有具有数量的项目,是否有交易。当项目没有交易时,数量将为0。
客户(C)
id | Name
1 | C1
2 | C2
3 | C3
项目(I)
id | Name
1 | I1
2 | I2
3 | I3
4 | I4
交易
id | C_id | I_id | qty | date
1 | C1 | I1 | 10 | 2/2/2016
2 | C2 | I3 | 5 | 3/2/2016
3 | C1 | I2 | 3 | 3/2/2016
4 | C2 | I1 | 8 | 4/2/2016
5 | C1 | I1 | 2 | 5/2/2016
6 | C1 | I2 | 4 | 5/2/2016
7 | C2 | I1 | 2 | 6/2/2016
8 | C1 | I1 | 100 | 1/3/2016
9 | C2 | I2 | 200 | 2/3/2016
我想要的2016年2月2日到2016年2月2日之间数据的结果是:
C | I | qty
C1 | I1 | 12
C1 | I2 | 7
C1 | I3 | 0
C1 | I4 | 0
C2 | I1 | 10
C2 | I2 | 0
C2 | I3 | 5
C2 | I4 | 0
C3 | I1 | 0
C3 | I2 | 0
C3 | I3 | 0
C4 | I4 | 0
答案 0 :(得分:3)
如果您想要包含所有商品的所有客户的完整列表,那么您将希望交叉加入这两个表。然后,您可以使用您所追踪的日期范围对事务表进行左连接。
让我们制作您的测试数据;
IF OBJECT_ID('tempdb..#Customers') IS NOT NULL DROP TABLE #Customers
GO
CREATE TABLE #Customers (id int, Name varchar(2))
INSERT INTO #Customers (id, Name)
VALUES
(1,'C1')
,(2,'C2')
,(3,'C3')
IF OBJECT_ID('tempdb..#Items') IS NOT NULL DROP TABLE #Items
GO
CREATE TABLE #Items (id int, Name varchar(2))
INSERT INTO #Items (id, Name)
VALUES
(1,'I1')
,(2,'I2')
,(3,'I3')
,(4,'I4')
IF OBJECT_ID('tempdb..#Transactions') IS NOT NULL DROP TABLE #Transactions
GO
CREATE TABLE #Transactions (id int, C_id varchar(2), I_id varchar(2), qty int, date datetime)
INSERT INTO #Transactions (id, C_id, I_id, qty, date)
VALUES
(1,'C1','I1',10,'2016-02-02')
,(2,'C2','I3',5,'2016-02-03')
,(3,'C1','I2',3,'2016-02-03')
,(4,'C2','I1',8,'2016-02-04')
,(5,'C1','I1',2,'2016-02-05')
,(6,'C1','I2',4,'2016-02-05')
,(7,'C2','I1',2,'2016-02-06')
,(8,'C1','I1',100,'2016-03-01')
,(9,'C2','I2',200,'2016-03-02')
您需要的查询;
DECLARE @StartDate datetime; SET @StartDate = '2016-02-02'
DECLARE @EndDate datetime; SET @EndDate = '2016-02-10'
SELECT
c.Name Cust_ID
,i.Name Item_ID
,SUM(ISNULL(t.qty,0)) Qty
FROM #Customers c
CROSS JOIN #Items i
LEFT JOIN #Transactions t
ON c.Name = t.C_id
AND i.Name = t.I_id
AND t.date BETWEEN @StartDate AND @EndDate
GROUP BY c.Name, i.Name
ORDER BY c.Name, i.Name
给出这些结果;
Cust_ID Item_ID Qty
C1 I1 12
C1 I2 7
C1 I3 0
C1 I4 0
C2 I1 10
C2 I2 0
C2 I3 5
C2 I4 0
C3 I1 0
C3 I2 0
C3 I3 0
C3 I4 0
答案 1 :(得分:1)
试试这个,希望这对你有所帮助。
select c.name,i.name,sum(isnull(t.qty,0))
from customers c
cross join Items I
left join transactions t on t.C_Id = C.Id and I.Id = t.I_Id and t.date between '2/2/2016' and '10/2/2016'
group by c.name,i.name
order by c.name,i.name