【问题标题】:SQL: 3 self-joins and then join them togetherSQL:3个自连接,然后将它们连接在一起
【发布时间】:2010-10-18 08:33:45
【问题描述】:

我有 2 个表格要以特定方式加入。我认为我的查询是正确的,但不确定。

select t1.userID, t3.Answer Unit, t5.Answer Demo  
FROM    
    table1 t1  
    inner join (select * from table2) t3 ON t1.userID = t3.userID   
    inner join (select * from table2) t5 ON t1.userID = t5.userID  
where  
    NOT EXISTS (SELECT * FROM table1 t2 WHERE t2.userID = t1.userID AND t2.date > t1.date)  
    and NOT EXISTS (SELECT * FROM table2 t4 WHERE t4.userID = t3.userID and t4.counter > t3.counter)  
    and NOT EXISTS (SELECT * FROM table2 t6 WHERE t6.userID = t5.userID and t6.counter > t5.counter)  
    and t1.date_submitted >'1/1/2009'  
    and t3.question = Unit  
    and t5.question = Demo  
order by  
    t1.userID  

从 table1 我想要不同的用户 ID,其中日期 > 1/1/2009

table1      
userID    Date
1         1/2/2009  
1         1/2/2009  
2         1/2/2009  
3         1/2/2009  
4         1/1/2008  

所以我想从 table1 得到的结果应该是这样的:

userID  
1  
2  
3  

然后我想在 userID 上用 table2 加入这个,看起来像这样:

table2 
userID    question   answer   counter
1         Unit       A        1
1         Demo       x        1
1         Prod       100      1
2         Unit       B        1
2         Demo       Y        1
3         Prod       100      1
4         Unit       A        1
1         Unit       B        2
1         Demo       x        2
1         Prod       100      2
2         Unit       B        2
2         Demo       Z        2
3         Prod       100      2
4         Unit       A        2

我想用这个结果将 table1 与 table2 连接起来:

userID    Unit    Demo
1         B       X
2         B       Z

换句话说,
从 table2 中选择不同的用户 ID,其中问题 = 最高计数器的单位
然后
从 table2 中选择不同的 userID,其中 question = Demo 为最高计数器。

我认为我所做的是 3 个自连接,然后将这 3 个连接在一起。

你觉得对吗?

【问题讨论】:

  • “你觉得对吗?” - 你运行它时它给出了正确的答案吗?
  • 我认为它给了我正确的答案,我只是想知道你是否能看出它有什么问题。我们使用的是 SQL 2005。谢谢
  • 我的查询肯定不对。还是有问题。

标签: sql sql-server sql-server-2005 join


【解决方案1】:
SELECT  du.userID, unit.answer, demo.answer
FROM    (
        SELECT  DISTINCT userID
        FROM    table1
        WHERE   date > '1/1/2009'
        ) du
LEFT JOIN
        table2 unit
ON      (userID, question, counter) IN
        (
        SELECT  du.userID, 'Unit', MAX(counter)
        FROM    table2 td
        WHERE   userID = du.userID
                AND question = 'Unit'
        )
LEFT JOIN
        table2 demo
ON      (userID, question, counter) IN
        (
        SELECT  du.userID, 'Demo', MAX(counter)
        FROM    table2 td
        WHERE   userID = du.userID
                AND question = 'Demo'
        )

table2 (userID, question, counter) 上建立索引将大大改进此查询。

既然你提到了SQL Server 2005,下面会更简单高效:

SELECT  du.userID,
        (
        SELECT  TOP 1 answer
        FROM    table2 ti
        WHERE   ti.user = du.userID
                AND ti.question = 'Unit'
        ORDER BY
                counter DESC
        ) AS unit_answer,
        (
        SELECT  TOP 1 answer
        FROM    table2 ti
        WHERE   ti.user = du.userID
                AND ti.question = 'Demo'
        ORDER BY
                counter DESC
        ) AS demo_answer
FROM    (
        SELECT  DISTINCT userID
        WHERE   date > '1/1/2009'
        FROM    table1
        ) du

聚合:

SELECT  answer, COUNT(*)
FROM    (
        SELECT  DISTINCT userID
        FROM    table1
        WHERE   date > '1/1/2009'
        ) du
JOIN    table2 t2
ON      t2.userID = du.userID
        AND t2.question = 'Unit'
GROUP BY
        answer

【讨论】:

  • 当我尝试运行它时,我得到一个错误:无效的列名'maxcnt'。我在 sql server 管理工作室工作。另外,我需要每个“用户 ID 和问题”的最大计数,而不是整个表的最大总计数。能做到吗?
  • 谢谢,但还是有问题。我将第一行更改为选择 *,这样我就可以看到所有数据正在返回。除 userID 列之外的所有列中的所有记录均为空。没有数据!应该有的。
  • 您说的是最后一个查询与 TOP 1 的关系?
  • 我不敢相信。我认为第二个对我有用。我得研究一下。谢谢夸西诺伊。
  • 不客气,但如果它适合您,请接受答案,以便我最终获得 10K。不是我很在意,但是,你知道... :)
猜你喜欢
  • 2016-05-27
  • 2013-06-30
  • 1970-01-01
  • 1970-01-01
  • 2011-01-21
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2017-06-30
相关资源
最近更新 更多