【问题标题】:How to Select rows in a table with all matching conditions in joining table如何在连接表中选择具有所有匹配条件的表中的行
【发布时间】:2017-10-23 14:36:04
【问题描述】:

我有两个表(表 A)和(表 B)以及一个表变量(@country),它们将构建 where 条件来查找与国家/地区匹配的员工列表。

TableA(empId, name)

(1,约翰),(2,玛丽),(3,哈利)

TableB(empId, country)

(1,澳大利亚),(1,US),(1,UK),(2,US)

例如,我只需要从 TableA 中选择同时居住在澳大利亚和美国的员工。即emp 1(约翰)。如果需要,查询应该能够在 where 子句中处理更多国家/地区。这取决于表变量@country 中的国家/地区数量。

我尝试了很多选项,包括以下查询,但似乎没有任何效果。

 DECLARE @country TABLE (
        [country]   [nvarchar](255) NOT NULL
 );

 insert into @country (country) values('Australia'),('US')

Select E.empID, EC.empID,EC.country from TableA E
INNER JOIN  TableB EC on E.empID= EC.empID
Where EC.country = ALL(Select country from @country)

您能否建议如何编写最佳查询来完成此任务?请注意,@country 可以有一个或多个国家/地区。

【问题讨论】:

  • 在选择中EC.country 应该是USAustralia
  • 不知道为什么你需要这个国家
  • @kbball 我需要国家,因为它将包含所有需要搜索的国家。在我的问题中,为了简单起见,我以澳大利亚和美国为例,但实际上它可以是 1 个或多个国家/地区。
  • 那么在这种情况下,您希望每个 empid 多行吗?
  • @kbball 是的,有可能

标签: sql sql-server tsql


【解决方案1】:

试试:

SELECT E.empID
    ,EC.empID
    ,EC.country
FROM TableA E
INNER JOIN TableB EC
    ON E.empID = EC.empID
WHERE EXISTS (
        SELECT 1 
        FROM TableB EC_US
        WHERE EC_US.empID = EC.empID
            and EC_US.Country = 'US'
    )
    AND EXISTS (
        SELECT 1 
        FROM TableB EC_Aus
        WHERE EC_Aus.empID = EC.empID
            and EC_Aus.Country = 'Australia'
    )

或者:

SELECT E.empID
    ,EC.empID
    ,EC.country
FROM TableA E
INNER JOIN TableB EC
    ON E.empID = EC.empID
WHERE EC.empID IN (
        SELECT EC_Sub.empID
        FROM TableB EC_Sub
        WHERE EC_Sub.Country IN ('Australia','US')
        GROUP BY EC_Sub.empID
        HAVING COUNT(*) = 2
    )

【讨论】:

  • 您将在第一个查询中返回重复的行 - 其中 EC.country 是美国,一个是澳大利亚。不确定 OP 想要哪一个或为什么国家/地区包含在示例查询中。
  • @kbball 在没有所需输出的情况下,我选择按照他发布的查询进行操作。这或许不是他想要的结果,但却是他暗中要求的结果。如果您有不同的解释或答案,我们鼓励您发布自己的答案。
  • @Bacon 如果@country 有更多的国家呢?您的查询在那里失败。
【解决方案2】:

立即尝试,添加了 where 子句。更改@country 的任意值并执行查询:

DECLARE @TableA TABLE (empId INT, [Name] VARCHAR(100))

INSERT INTO @TableA VALUES (1, 'John')
INSERT INTO @TableA VALUES (2, 'Mary')
INSERT INTO @TableA VALUES (3, 'Harry')

DECLARE @TableB TABLE (empID INT, country VARCHAR(100))

INSERT INTO @TableB VALUES (1, 'Australia')
INSERT INTO @TableB VALUES (1, 'UK')
INSERT INTO @TableB VALUES (2, 'US')


 DECLARE @country TABLE ([country] [nvarchar](255) NOT NULL);

 INSERT INTO @country (country) VALUES('Australia'),('US')

SELECT a.* , tb.country
FROM   @TableA AS a
       INNER JOIN (
                SELECT b.empid,
                       COUNT(*)  AS empInMultipleCountry
                FROM   @TableB      b   
                GROUP BY
                       empid
            ) b
            ON  a.empId = b.empid
     INNER JOIN @TableB AS tb
            ON tb.empId = a.empId

WHERE  empInMultipleCountry > 1
AND EXISTS (SELECT 1 FROM @country AS c WHERE c.country = tb.country)

【讨论】:

  • 不回答原始问题。 “where”子句在哪里?
【解决方案3】:
Select E.empID, EC.empID,EC.country 
from TableA E INNER JOIN TableB EC on E.empID= EC.empID
Where EC.country IN ('Australia','US');

【讨论】:

  • 不,这也会选择 empId 2 (Mary)。我需要同时拥有“澳大利亚和美国”作为国家/地区的人
猜你喜欢
  • 1970-01-01
  • 2013-03-31
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2015-09-13
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多