繁体   English   中英

将包含相同ID但数据不同的两行合并为一行

[英]Merge two rows that contain the same Id but different data into one row

我对大家有一个非常棘手的问题

假设我有下表

AccountType

Id       Type
 1     Checking
 2      Savings 

Customer_Account

Customer_Id      Account_Type_Id
    450                 1
    450                 2
    451                 1

Customer_Account包含客户ID和其帐户类型ID的列表。 Account_Type_Id是来自AccountType.Id的外键。

假设在Customer_Account表中,名为Josh(id 450)的客户可以同时具有支票帐户和储蓄帐户,如上所示。 我可以通过在AccountType表上两次进行一次LEFT JOIN来输出此客户及其ID和帐户类型:

SELECT CustAccount.Customer_Id AS Id, Account1.Type AS Account_Type_1, Account2.Type AS Account_Type_2
FROM Customer_Account CustAccount
LEFT JOIN AccountType Account1
ON Account1.Id = CustAccount.Account_Type_Id
LEFT JOIN AccountType Account2
ON Account2.Id = CustAccount.Account_Type_Id

输出将是:

 Id        Account_Type_1         Account_Type_2           
450           Checking               Checking 
450           Savings                Savings
451           Checking               Checking   

我要尝试做的是,如果像Josh(id 450)这样的客户同时拥有支票账户和储蓄账户,我想将上述两行数据输出为一行,如下所示:

 Id        Account_Type_1      Account_Type_2
450           Checking            Savings

而且,如果客户只有一种类型的帐户(例如此处的ID为451的客户),我只希望该类型的帐户出现在相应的列下,如下所示:

 Id        Account_Type_1      Account_Type_2
451           Checking            

或者,如果ID为451的客户只有一个储蓄帐户,则输出应为:

Id        Account_Type_1      Account_Type_2
451                              Savings

我希望“检查”仅显示在Accoun_Type_1下,而“储蓄”显示在Account_Type_2下。 如果我执行GROUP BY CustAccount.Customer_Id,则会得到以下信息:

 Id        Account_Type_1      Account_Type_2
450           Checking            Checking
451           Checking            Checking

任何专家的帮助将不胜感激。

谢谢。

这看起来像是FULL OUTER JOIN的简单应用程序:

SELECT COALESCE(ac1.id, ac2.id) AS id, ac1.Account_Type_1, ac2.Account_Type_2
  FROM (SELECT c.Customer_ID AS Id, t.Type AS Account_Type_1
          FROM Customer_Account AS c
          JOIN AccountType      AS t ON c.Account_Type_ID = t.ID AND t.ID = 1) AS ac1
  FULL OUTER JOIN
       (SELECT c.Customer_ID AS Id, t.Type AS Account_Type_2
          FROM Customer_Account AS c
          JOIN AccountType      AS t ON c.Account_Type_ID = t.ID AND t.ID = 2) AS ac2
    ON ac1.Id = ac2.Id;

如果您的DBMS不支持FULL OUTER JOIN但支持LEFT OUTER JOIN,则可以使用:

SELECT ac0.id, ac1.Account_Type_1, ac2.Account_Type_2
  FROM (SELECT DISTINCT c.Customer_ID AS Id FROM Customer_Account AS c) AS ac0
  LEFT OUTER JOIN
       (SELECT c.Customer_ID AS Id, t.Type AS Account_Type_1
          FROM Customer_Account AS c
          JOIN AccountType      AS t ON c.Account_Type_ID = t.ID AND t.ID = 1) AS ac1
    ON ac0.id = ac1.id
  LEFT OUTER JOIN
       (SELECT c.Customer_ID AS Id, t.Type AS Account_Type_2
          FROM Customer_Account AS c
          JOIN AccountType      AS t ON c.Account_Type_ID = t.ID AND t.ID = 2) AS ac2
    ON ac0.Id = ac2.Id;

第一个子查询生成存在的客户ID列表; 第二个生成帐户类型1(检查)的列表; 第三个生成帐户类型2(保存)的列表。 联接可确保正确识别每个帐户。

我认为应该对您有帮助

1Sql选择查询问题。 合并行或其他

应该对你有帮助

为您的ON子句添加更多条件:

ON Account1.Id = CustAccount.Account_Type_Id and Account1.Account_Type_Id = 1

ON Account2.Id = CustAccount.Account_Type_Id and Account2.Account_Type_Id = 2

将导致输出包括客户持有的帐户。 如果他们只有一个帐户,则另一帐户类型将为NULL。

编辑:对不起,我没有意识到您没有客户表。 您可以使用不同的Customer_Id值列表创建一个临时表,并将其用作JOIN中的第一个表。

select distinct Customer_Id into #Customers
    from Customer_Account

或者更简单:

select distinct C.Customer_Id,
    ( select 'Checking' from Customer_Account where Customer_Id = C.CustomerId and Account_type_Id = 1 ) as Account_Type_1,
    ( select 'Savings' from Customer_Account where Customer_Id = C.CustomerId and Account_type_Id = 2 ) as Account_Type_2,
    from Customer_Account as C

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM