只查询返回匹配数据

Bel*_*igh 0 sql-server t-sql sql-server-2008-r2

我正在尝试使用左外连接从两个表中返回数据。MetaKnight 拥有最多的 storeNames,我希望所有这些都返回,当然还有来自 KnightNinja 的相应数据。我把下面的语法放在一起,但我的语法只返回两个表中符合条件的商店的名称。例如,应该返回 Store D 和 Store E,因为日期是 2017 年 1 月 - 但语法不会返回它。为什么?

这是示例垃圾 DDL 和查询

Create Table MetaKnight
(
    storeName varchar(500) NOT NULL
    ,storeNumber varchar(100) NOT NULL Primary Key
    ,openDate date NOT NULL
)

Create NonClustered Index snIndex
On MetaKnight (storeName ASC)

Create Table KnightNinja 
(
    storeName varchar(500) NOT NULL
    ,ssID varchar(100) NOT NULL Primary Key
    ,c1 int not null Default(0)
    ,c2 int not null Default(0)
    ,c3 int not null Default(0)
    ,c4 int not null Default(0)
    ,d1 date not null
)

Create NonClustered Index storeIndex
On KnightNinja (storeName ASC)

Insert Into KnightNinja (storeName, ssID, c1, c2, c3, c4, d1) Values
('Store A', '1234', '7018', '0',    '4635', '6',    '2017-03-13'),
('Store B', '5678', '0',    '0',    '0',    '0',    '2017-01-28'),
('Store C', '9101', '219',  '898',  '154',  '11',   '2017-01-10'),
('Store D', '8842', '25019',    '258947',   '5746', '0',    '2017-01-31'),
('Store E', '6643', '26682',    '25920',    '3410', '281',  '2017-02-15'),
('Store F', '2211', '57',   '0',    '392',  '22',   '2017-03-11'),
('Store G', '1432', '398',  '1007', '407',  '0',    '2017-01-10'),
('Store G', '8879', '534',  '3125', '954',  '19',   '2017-03-11'),
('Store H', '8675', '40',   '0',    '146',  '147',  '2017-01-01'),
('Store I', '2411', '0',    '4899', '0',    '0',    '2017-01-20')

INSERT INTO MetaKnight (storeName, storeNumber, openDate) Values
('Store A', '2.2',  '2017-01-19'),
('Store B', '8103', '2017-10-25'),
('Store C', '5522', '2017-10-25'),
('Store D', 'Blue', '2017-09-26'),
('Store E', 'B6565','2017-04-28'),
('Store G', 'E999', '2017-01-14'),
('Store G', 'L1354','2017-01-14'),
('Store G', 'R2288','2017-01-14'),
('Store H', 'A5678','2017-01-28'),
('Store I', 'C1234','2017-01-14')

Select 
mk.storeName
,[Ninja Count] = COUNT(kn.ssID)
,[Meta Count] = COUNT(mk.storeNumber)
,[C1 Total] = SUM(COALESCE(kn.c1,0))
,[C2 Total] = SUM(COALESCE(kn.c2,0))
,[C3 Total] = SUM(COALESCE(kn.c3,0))
,[C4 Total] = SUM(COALESCE(kn.c4,0))
FROM MetaKnight mk
LEFT OUTER JOIN KnightNinja kn
ON mk.storeName = kn.storeName
AND kn.d1 >= '2017-01-01'
AND kn.d1 < '2017-02-01'
WHERE mk.openDate >= '2017-01-01'
AND mk.openDate < '2017-02-01'
GROUP BY mk.storeName
ORDER BY mk.storeName ASC

Drop Table KnightNinja
Drop Table MetaKnight
Run Code Online (Sandbox Code Playgroud)

McN*_*ets 5

看看Aaron Bertrand 的这个有趣的答案,你会得到关于正在发生的事情的详细答案。

从左表返回所有数据

您应该将 WHERE 子句的所有条件移动到 LEFT JOIN 子句。

Select mk.storeName
       ,[Ninja Count] = COUNT(kn.ssID)
       ,[Meta Count] = COUNT(mk.storeNumber)
       ,[C1 Total] = SUM(COALESCE(kn.c1,0))
       ,[C2 Total] = SUM(COALESCE(kn.c2,0))
       ,[C3 Total] = SUM(COALESCE(kn.c3,0))
       ,[C4 Total] = SUM(COALESCE(kn.c4,0))
FROM   MetaKnight mk
LEFT OUTER JOIN KnightNinja kn
ON     mk.storeName = kn.storeName
AND    kn.d1 >= '2017-01-01'
AND    kn.d1 < '2017-02-01'
AND    mk.openDate >= '2017-01-01'
AND    mk.openDate < '2017-02-01'
GROUP BY mk.storeName
ORDER BY mk.storeName ASC

GO
Run Code Online (Sandbox Code Playgroud)
店名 | 忍者伯爵| 元计数 | C1 总计 | C2 总计 | C3 总计 | C4 总计
:-------- | ----------: | ---------: | -------: | -------: | -------: | -------:
店铺 A | 0 | 1 | 0 | 0 | 0 | 0
店铺 B | 0 | 1 | 0 | 0 | 0 | 0
店铺 C | 0 | 1 | 0 | 0 | 0 | 0
店铺 D | 0 | 1 | 0 | 0 | 0 | 0
商店 E | 0 | 1 | 0 | 0 | 0 | 0
商店 G | 3 | 3 | 第1194章 3021 | 第1221章 0
店铺 H | 1 | 1 | 40 | 0 | 146 | 147
店铺我 | 1 | 1 | 0 | 4899 | 0 | 0

警告:空值被聚合或其他 SET 操作消除。

dbfiddle在这里

更新

在这种情况下会出现问题,因为您的查询都没有返回 all storeName

SELECT    mk.storeName,
         [Meta Count] = COUNT(mk.storeNumber)
FROM      MetaKnight mk
WHERE     mk.openDate >= '2017-01-01'
AND       mk.openDate < '2017-02-01'
GROUP BY  mk.storeName;
Run Code Online (Sandbox Code Playgroud)
店名 | 元计数
:-------- | ---------:
店铺 A | 1
商店 G | 3
店铺 H | 1
店铺我 | 1
SELECT   kn.storeName, 
         [Ninja Count] = COUNT(kn.ssID),
         [C1 Total] = SUM(COALESCE(kn.c1,0)),
         [C2 Total] = SUM(COALESCE(kn.c2,0)),
         [C3 Total] = SUM(COALESCE(kn.c3,0)),
         [C4 Total] = SUM(COALESCE(kn.c4,0))
FROM     KnightNinja kn
WHERE    kn.d1 >= '2017-01-01'
AND      kn.d1 < '2017-02-01'
GROUP BY kn.storeName
GO
Run Code Online (Sandbox Code Playgroud)
店名 | 忍者伯爵| C1 总计 | C2 总计 | C3 总计 | C4 总计
:-------- | ----------: | -------: | -------: | -------: | -------:
店铺 B | 1 | 0 | 0 | 0 | 0
店铺 C | 1 | 第219话 第898话 154 | 11
店铺 D | 1 | 25019 | 258947 | 5746 | 0
商店 G | 1 | 第398话 1007 | 407 | 0
店铺 H | 1 | 40 | 0 | 146 | 147
店铺我 | 1 | 0 | 4899 | 0 | 0

让我建议另一种方法:

WITH sn AS
(
    SELECT DISTINCT storeName
    FROM MetaKnight
)
SELECT sn.storeName,               
       kn1.[Ninja Count],
       cnt.[Meta Count],
       kn1.[C1 Total],
       kn1.[C2 Total],
       kn1.[C3 Total],
       kn1.[C4 Total]
FROM   sn
LEFT JOIN (SELECT    mk.storeName
                    ,[Meta Count] = COUNT(mk.storeNumber)
           FROM      MetaKnight mk
           WHERE     mk.openDate >= '2017-01-01'
           AND       mk.openDate < '2017-02-01'
           GROUP BY  mk.storeName) cnt
ON        sn.storeName = cnt.storeName
LEFT JOIN (SELECT   kn.storeName, 
                    [Ninja Count] = COUNT(kn.ssID),
                    [C1 Total] = SUM(COALESCE(kn.c1,0)),
                    [C2 Total] = SUM(COALESCE(kn.c2,0)),
                    [C3 Total] = SUM(COALESCE(kn.c3,0)),
                    [C4 Total] = SUM(COALESCE(kn.c4,0))
           FROM     KnightNinja kn
           WHERE    kn.d1 >= '2017-01-01'
           AND      kn.d1 < '2017-02-01'
           GROUP BY kn.storeName) kn1
ON        sn.storeName = kn1.storeName
ORDER BY  sn.storeName ASC

GO
Run Code Online (Sandbox Code Playgroud)
店名 | 忍者伯爵| 元计数 | C1 总计 | C2 总计 | C3 总计 | C4 总计
:-------- | ----------: | ---------: | -------: | -------: | -------: | -------:
店铺 A |        | 1 |     |     |     |     null
店铺 B | 1 |       | 0 | 0 | 0 | 0
店铺 C | 1 |       | 第219话 第898话 154 | 11
店铺 D | 1 |       | 25019 | 258947 | 5746 | 0
商店 E |        |       |     |     |     |     空值
商店 G | 1 | 3 | 第398话 1007 | 407 | 0
店铺 H | 1 | 1 | 40 | 0 | 146 | 147
店铺我 | 1 | 1 | 0 | 4899 | 0 | 0

dbfiddle在这里