sql 连接两个相似的子查询

sql join between two subqueries that are similar

我是 SQL 的初学者。我有两个table,一个是student_records,另一个是table student_fees,里面有学生打折的记录(fee_type_code=2)以及按常规收费 (fee_type_code=1) 的收费。费用类型的代码是 fee_type_code。系统存在错误,导致一些学生同时获得两种费用类型。我想获取所有的错误记录。首先,我有两个单独运行良好的查询,但我试图将它们合并到一个查询中,然后在临时 tables:

上创建一个连接
select 
student_id, fee_type_code 
from
      ((select * from student_records r, student_fees f 
        where s.student_id=f.student_id and fee_type_code=1) A 
        inner join 
       (select * from student_records r, student_fees f 
        where       
        s.student_id=f.student_id and fee_type_code=2) B 
       on A.student_id=B.student_id);

对于给您带来的任何不便,或者如果这个问题太天真,我深表歉意,但我陷入了困境。我得到的错误是 "Reference to student_id is ambiguous..."

如果我对你的问题的理解正确,你正在寻找具有 fee_type_codes12 的学生。

这应该可以满足您的要求:

Select  R.student_id
From    Student_records R
Join    Student_fees    F   On  R.Student_id = F.Student_id
Where   F.fee_type_code In (1, 2)
Group By R.student_id
Having Count(Distinct F.fee_type_code) = 2

如果您的目标是获得具有两种费用类型的学生列表,那么您可以使用 group byhaving 代替:

select sr.student_id
from student_records sr
join student_fees sf on sr.student_id = sf.student_id
where sf.fee_type_code in (1,2)
group by sr.student_id
having count(distinct sf.fee_type_code) = 2

正如其他人之前提到的,您可以使用一些语法上更简单的技术来获取此数据集,但我想确保您了解原始查询的问题所在。

解释

"Reference to student_id is ambiguous..."

您在 SELECT 语句中选择了 student_idfee_type_code 但实际上您在子查询中两次引用了这些字段(一次在子查询 A 中,一次在子查询 B)。 SQL 引擎不够智能,无法识别这些代表相同数据的副本,因此它无法决定您要查看哪个子查询字段。要按照您最初设计的方式完成查询,您需要明确告诉 SQL 引擎您希望在 SELECT 中看到哪些字段:

select A.student_id, A.fee_type_code --This can be A or B fields as they represent the
                                    -- same records but a table must be defined
from
  ((select student_id, fee_type_code 
    from student_records r, student_fees f 
    where s.student_id=f.student_id and fee_type_code=1) A 
    inner join 
   (select student_id, fee_type_code 
    from student_records r, student_fees f 
    where s.student_id=f.student_id and fee_type_code=2) B 
       on A.student_id=B.student_id);