在SQL中加入后计算具有相同值的行

时间:2012-08-16 21:29:04

标签: sql sql-server count jointable

如何添加一列显示两列中具有相同值的总行数,并且已连接多个表。在所有连接和where语句之后,我最终得到一个包含以下列的表:

产品|政策号码|行号|认可名称

表中有更多列,但这些是我需要引用的列。 从产品到政策编号之间存在一对多的关系,从政策编号到行号的一对多关系,以及从行号到背书可能的一对多关系或没有匹配关系。

这就是查询现在的样子:

Select pd.ProductName AS Product
,p.PolicyNumber AS Policy
,l.LineNumber AS Line
,e.EndorsementName AS Endorsement

FROM Lines l
INNER JOIN Policies p On p.PolicyID = l.PolicyID
LEFT OUTER JOIN Endorsements e on e.EndorsementID = l.EndorsementID
INNER JOIN Product pd on pd.ProductID = p.ProductID

结果表看起来像这样

Product     Policy     Line     Endorsement
CH           8001       1            A
CH           8001       2            A
CH           8001       3            A
CH           8001       3            B
CH           8002       1            D
CH           8002       2            D
CH           8002       3            A
PP           9001       1            NULL
PP           9001       2            NULL
PP           9002       1            A
PP           9002       2            A
PP           9002       2            B

我需要做的是计算每个政策行的认可数量。在上面的示例中,我会看到对于产品CH,唯一具有多个认可的订单项是政策8001 - 第3行。对于产品PP,唯一具有多个认可的订单项是政策9002 - 第2行。

我想要的第一件事是一个新列,它显示每一行的计数,显示该行的相同策略和行值的总出现次数。该表将如下所示:

Product     Policy     Line     Endorsement     Line Endorsement Count
CH           8001       1            A                   1
CH           8001       2            A                   1
CH           8001       3            A                   2
CH           8001       3            B                   2
CH           8002       1            D                   1
CH           8002       2            D                   1
CH           8002       3            A                   1
PP           9001       1            A                   1
PP           9001       2            A                   1
PP           9002       1            A                   1
PP           9002       2            A                   2
PP           9002       2            B                   2

在我成功实现此计数之后,我想要一个单独的查询,该查询只返回没有任何具有多个认可的行的策略的行,因此在这种情况下,策略8001和9002将不会显示。

我已经尝试过GROUP BYHAVING以及我在不同帖子中看到的各种不同的事情,并根据我的需要进行调整,但未找到适用于此特定示例的解决方案。请记住,我也已经有很多WHERE语句和一些Order By。

修改 我正在使用Microsoft SQL Server Management Studio 2010来执行这些查询

谢谢!

2 个答案:

答案 0 :(得分:4)

这取决于数据库。如果你有窗口功能,你可以很简单地做到:

Select pd.ProductName as Product, p.PolicyNumber as Policy,
       l.LineNumber Line, e.EndorsementName as Endorsement,
       count(*) over (partition by policy, line) as Policy_Line_Count
FROM Lines l INNER JOIN
     Policies p
     On p.PolicyID = l.PolicyID LEFT OUTER JOIN
     Endorsements e
     on e.EndorsementID = l.EndorsementID INNER JOIN
     Product pd
     on pd.ProductID = p.ProductID

如果您没有Windows函数,则可以使用WITH语句来简化查询:

with t as (
         Select pd.ProductName as Product, p.PolicyNumber as Policy,
            l.LineNumber Line, e.EndorsementName as Endorsement
     FROM Lines l INNER JOIN
          Policies p
          On p.PolicyID = l.PolicyID LEFT OUTER JOIN
          Endorsements e
          on e.EndorsementID = l.EndorsementID INNER JOIN
          Product pd
          on pd.ProductID = p.ProductID
   )
select t.*, tpl.cnt
from t join
     (select Policy, Line, count(*) as cnt
      from t
      group by Policy, Line
     ) tpl
     on t.Policy = tpl.Policy and
        t.Line= tpl.Line

最后,您可能正在使用既没有WITH语句也没有windows函数的mysql。在这种情况下,您可以创建视图并使用上述查询。或者,您可以将原始查询放在临时表中并使用上面的查询。或者,您接受原始查询并按照示例重复两次。

答案 1 :(得分:0)

给它一个旋转:

Select pd.ProductName AS Product
,p.PolicyNumber AS Policy
,l.LineNumber AS Line
,e.EndorsementName AS Endorsement
,cnt

FROM Lines l
INNER JOIN Policies p On p.PolicyID = l.PolicyID
LEFT OUTER JOIN Endorsements e on e.EndorsementID = l.EndorsementID
INNER JOIN Product pd on pd.ProductID = p.ProductID
INNER JOIN (
    Select pd.ProductName AS subProduct
    ,p.PolicyNumber AS subPolicy
    ,l.LineNumber AS subLine
    ,COUNT(*) AS cnt

    FROM Lines l
    INNER JOIN Policies p On p.PolicyID = l.PolicyID
    INNER JOIN Product pd on pd.ProductID = p.ProductID
    GROUP BY pd.ProductName, p.PolicyNumber, l.LineNumber
    ) AS Sub ON pd.ProductName = subProduct, p.PolicyNumber = subPolicy, l.LineNumber = subLine