SQL中的级联/条件JOIN

时间:2012-04-17 14:20:27

标签: sql oracle

我目前正在三个领域加入两个表:

SELECT t1.A, t1.B, t1.C, t2.D
  FROM t1, t2
 WHERE t1.A = t2.A
   AND t1.B = t2.B
   AND t1.C = t2.C

由于我的数据的工作方式,如果连接在A / B / C上不匹配,那么我想加入A / B.如果该连接不匹配,那么我只想加入A.这种类型的级联连接是否可以在SQL查询中使用(我使用的是Oracle 10g)?或者我必须用代码处理这个吗?

3 个答案:

答案 0 :(得分:2)

这对你有用吗?

  SELECT DISTINCT 
         t1.A,
         t1.B,
         t1.C,
         t2.D
    FROM t1, t2
   WHERE (t1.A = t2.A
          AND t1.B = t2.B
          AND t1.C = t2.C)
      OR (t1.A = t2.A
          AND t1.B = t2.B)
      OR (t1.A = t2.A);

修改

如果你想要所有的结果,但想看看它们是如何匹配的那么你可以发出这个:

   SELECT t1.A,
          t1.B,
          t1.C,
          t2.D,
          (CASE 
              WHEN t1.A = t2.A
               AND t1.B = t2.B
               AND t1.C = t2.C
              THEN 'A/B/C'
              WHEN t1.A = t2.A
               AND t1.B = t2.B
              THEN 'A/B'
              WHEN t1.A = t2.A
              THEN 'A'
              ELSE 'None'
           END) AS match_criteria
     FROM t1, t2
    WHERE t1.A = t2.A; 

在结果集中,您可以看到行的匹配级别,然后使用那里的数据。 也许通过将此查询包装在外部查询中,您可以丢弃您不想要的行,或者优先考虑您想要的行。

希望它有所帮助...

答案 1 :(得分:2)

您可以通过将三个查询联合在一起来执行此操作,并在两个更常规的查询中,排除在更具体的查询中返回的行。

如何确定要从更一般的查询中排除哪些行取决于数据的形状,但您可以尝试这样的事情:

SELECT t1.A, t1.B, t1.C, t2.D
  FROM t1, t2
 WHERE t1.A = t2.A AND t1.B = t2.B AND t1.C = t2.C
UNION 
SELECT t1.A, t1.B, t1.C, t2.D
  FROM t1, t2
 WHERE t1.A = t2.A AND t1.B = t2.B 
  AND NOT EXISTS (SELECT * FROM t2 WHERE t2.A = t1.A AND t2.B = t1.B AND t2.C = t1.C)
UNION
SELECT t1.A, t1.B, t1.C, t2.D
  FROM t1, t2
 WHERE t1.A = t2.A
  AND NOT EXISTS (SELECT * FROM t2 WHERE t2.A = t1.A AND t2.B = t1.B)

答案 2 :(得分:0)

SELECT t1.A, t1.B, t1.C, t2.D
  FROM t1
  LEFT JOIN t2
  ON t1.A = t2.A AND t1.B = t2.B AND t1.C = t2.C

试试这个并检查你是否喜欢这个结果,如果没有,请使用它(psedo.code):

insert into #temptable
SELECT t1.A, t1.B, t1.C, t2.D
  FROM t1, t2
  WHERE t1.A = t2.A AND t1.B = t2.B AND t1.C = t2.C

IF select count(*) from #temptable = 0 then
insert into #temptable
SELECT t1.A, t1.B, t1.C, t2.D
  FROM t1, t2
  WHERE t1.A = t2.A AND t1.B = t2.B
end if;


IF select count(*) from #temptable = 0 then
insert into #temptable
SELECT t1.A, t1.B, t1.C, t2.D
  FROM t1, t2
  WHERE t1.A = t2.A
end if;

select * from #temptable
drop #temptable