如何在SQL Server 2014中查找没有值的记录?

时间:2017-06-06 22:45:14

标签: sql sql-server

我有一个表'FinTrans',其数据如下所示:

---------------------------------
|AcctID     |TransCode |TransAmt|
---------------------------------
|1234567    |TOLL      |    4:30|
---------------------------------
|1234567    |PYMT      |    5:30|
---------------------------------
|1234567    |RFND      |    1:00|
---------------------------------
|2345678    |TOLL      |    4:30|
---------------------------------
|2345678    |TOLL      |    4:30|
---------------------------------
|2345678    |RFND      |    4:30|
---------------------------------
|3456789    |TOLL      |    4:30|
---------------------------------

我有一个'帐户'表,提供每个AcctID的帐号。

我需要找到没有'PYMT'作为TransCode的帐号。

我尝试过以下代码,但显然没有用。

SELECT DISTINCT(A.AccountNumber)      
      ,TransCode
      ,SUM(TransAmt)

  FROM FinTrans F
  INNER JOIN Account A ON F.AcctID = A.AccountID

  WHERE TransCode = 'TOLL'
    AND TransCode != 'PYMT'

  GROUP BY A.AccountNumber, TransCode

3 个答案:

答案 0 :(得分:1)

我需要找到没有'PYMT'作为TransCode

的帐号

你可以尝试这个......通过

使用群组
SELECT A.AccountNumber
      ,TransCode
      ,SUM(TransAmt)

  FROM FinTrans F
  INNER JOIN Account A ON F.AcctID = A.AccountID
  where TransCode IN ('PYMT', 'TOLL')
  GROUP BY A.AccountNumber, TransCode
  HAVING SUM(IIF(TransCode = 'PYMT',1,0)) = 0

答案 1 :(得分:1)

我认为这是执行NOT HAVING的正常方式:

SELECT AccountNumber
FROM Account AS a
WHERE NOT EXISTS (
      SELECT NULL FROM FinTrans AS f
      WHERE a.AccountID = f.AcctID AND
            f.TransCode = "PYMT")

尝试解释您的示例,我相信您正在寻找

SELECT a.AccountNumber, f.TransCode, SUM(f.TransAmt)
FROM FinTrans AS f
INNER JOIN Account AS a ON f.AcctID = a.AccountID
WHERE f.AcctID IN (SELECT f.AcctID FROM FinTrans AS F GROUP BY f.AcctID 
                   HAVING SUM(CASE WHEN f.TransCode = 'PYMT' THEN 1 ELSE 0 END) = 0)
      AND f.TransCode = 'TOLL'
GROUP BY f.AcctID

使用第一种过滤组的方法的另一个选项是

SELECT a.AccountNumber, f.TransCode, SUM(f.TransAmt)
FROM FinTrans AS f
INNER JOIN Account AS a ON f.AcctID = a.AccountID
WHERE f.AcctID IN (SELECT AcctID FROM FinTrans AS f 
                   WHERE NOT EXISTS (SELECT NULL FROM FinTrans AS f2
                                     WHERE f.AcctID = f2.AcctID AND f2.TransCode = "PYMT"))
                         AND f.TransCode = 'TOLL'
GROUP BY f.AcctID;

答案 2 :(得分:1)

您可以使用group byhaving

执行此操作
SELECT A.AccountNumber
FROM FinTrans F INNER JOIN
     Account A
     ON F.AcctID = A.AccountID
WHERE TransCode IN ('PYMT', 'TOLL')
GROUP BY A.AccountNumber
HAVING SUM(CASE WHEN TransCode = 'PYMT' THEN 1 ELSE 0 END) = 0;

您真的需要示例SQL中的其他列吗?它们与您的问题无关。

您也可以使用EXISTS / NOT EXISTS

执行此操作
select a.*
from account a
where exists (select 1
              from FinTrans f
              where f.AcctID = a.AccountID and f.TransCode = 'TOLL'
             ) and
      not exists (select 1
                  from FinTrans f
                  where f.AcctID = a.AccountID and f.TransCode = 'PYMT'
                 );

这具有不需要聚合的性能优势。