Sql 以第三个表为条件连接两个表

Sql 以第三个表为条件连接两个表,sql,tsql,subquery,azure-sql-database,inner-join,Sql,Tsql,Subquery,Azure Sql Database,Inner Join,我试图根据第三个表的条件创建两个表的视图。我有三张桌子: 客户 地址 帐目 我很难得出结果。我最终得到了萨曼莎的两张唱片。下面是我最新的查询工作;我做错了什么 SELECT ClientTable.client_id, ClientTable.first_name, AddressTable.account_id, AddressTable.street, AddressTable.city FROM [clients] ClientTable

我试图根据第三个表的条件创建两个表的视图。我有三张桌子:

客户

地址

帐目

我很难得出结果。我最终得到了萨曼莎的两张唱片。下面是我最新的查询工作;我做错了什么

SELECT
    ClientTable.client_id,
    ClientTable.first_name,
    AddressTable.account_id,
    AddressTable.street,
    AddressTable.city
FROM
    [clients] ClientTable
    INNER JOIN
    (
        SELECT
            [addresses].client_id,
            [addresses].account_id,
            [addresses].street,
            [addresses].city
        FROM [addresses]
        INNER JOIN [accounts] ON [addresses].client_id = [accounts].client_id
        WHERE [accounts].status <> 'cancelled'
    ) AddressTable ON ClientTable.client_id = AddressTable.client_id
您可以加入“客户端”和“地址”表,并使用“不存在”收回已取消的帐户:

select cl.client_id, cl.first_name, ad.account_id, ad.street, ad.city
from clients cl
inner join addresses ad on ad.client_id = cl.client_id
where not exists (
    select 1 
    from accounts ac 
    where 
        ac.client_id = ad.client_id 
        and ac.account_id = ad.account_id
        and ac.status = 'cancelled'
)
另一种方法使用帐户联接,正如您最初打算的那样:

select cl.client_id, cl.first_name, ad.account_id, ad.street, ad.city
from clients cl
inner join addresses ad on ad.client_id = cl.client_id
inner join accounts ac on ac.client_id = ad.client_id and ac.account_id = ad.account_id
where ac.status <> 'cancelled'
请注意,两个查询所做的事情并不完全相同;第二个查询需要一个状态为“未取消”的帐户,而第一个查询只是禁止取消帐户,不允许使用没有帐户的地址

-两个查询都产生:

client_id | first_name | account_id | street | city --------: | :--------- | :--------------- | :------------ | :-------- 10000000 | Samantha | BBBBBBBBBBBBBBBB | 111 Orange St | Hong Kong 10000001 | Andrew | CCCCCCCCCCCCCCCC | 456 Grape St | Amsterdam 10000002 | Audrey | DDDDDDDDDDDDDDDD | 789 Peach St | Toronto
你的第一种方法有一个问题:ac.account\u id=cl.account\u id,因为account\u id不是cl的一列。假设你的意思是,ac.account\u id=cl.account\u id,那么我仍然会得到萨曼莎的两个记录。同样,您的第二个用户试图比较:和ac.account\u id=ad.client\u id时也会抛出一个错误。假设您的意思是和ac.account\u id=ad.account\u id,我仍然会得到Samantha的两条记录。@Crayons:我修复了别名。我的回答中还添加了一个db提琴——萨曼莎只出现过一次。对不起@GMB,这个错误是我的。除了被取消之外,还有很多状态。我忘记了其他人。在对我的真实数据应用了适当的WHERE子句之后,您提出的两种解决方案都起了作用。很荣幸介绍了DB Fiddle,我不知道它的存在。根据我的测试,利用不存在的地方表现更好。干杯,伙计。
SELECT
    ClientTable.client_id,
    ClientTable.first_name,
    AddressTable.account_id,
    AddressTable.street,
    AddressTable.city
FROM
    [clients] ClientTable
    INNER JOIN
    (
        SELECT
            [addresses].client_id,
            [addresses].account_id,
            [addresses].street,
            [addresses].city
        FROM [addresses]
        INNER JOIN [accounts] ON [addresses].client_id = [accounts].client_id
        WHERE [accounts].status <> 'cancelled'
    ) AddressTable ON ClientTable.client_id = AddressTable.client_id
select cl.client_id, cl.first_name, ad.account_id, ad.street, ad.city
from clients cl
inner join addresses ad on ad.client_id = cl.client_id
where not exists (
    select 1 
    from accounts ac 
    where 
        ac.client_id = ad.client_id 
        and ac.account_id = ad.account_id
        and ac.status = 'cancelled'
)
select cl.client_id, cl.first_name, ad.account_id, ad.street, ad.city
from clients cl
inner join addresses ad on ad.client_id = cl.client_id
inner join accounts ac on ac.client_id = ad.client_id and ac.account_id = ad.account_id
where ac.status <> 'cancelled'
client_id | first_name | account_id | street | city --------: | :--------- | :--------------- | :------------ | :-------- 10000000 | Samantha | BBBBBBBBBBBBBBBB | 111 Orange St | Hong Kong 10000001 | Andrew | CCCCCCCCCCCCCCCC | 456 Grape St | Amsterdam 10000002 | Audrey | DDDDDDDDDDDDDDDD | 789 Peach St | Toronto