在sql条件下进行解码的外连接

时间:2014-12-31 18:12:53

标签: sql oracle

我从表table_a中获取列最新控件号。如果此表中的员工没有行,则它应返回null。为此,我创建了一个查询

表-A

control_num emp_num  approv_begin_date approv_end_date prov_end_date prov_begin_date
1           10        30-NOV-2014       30-JAN-2014     30-NOV-2014       30-JAN-2014  

表-B

EMP_NUM  NAM
10       XYZ
20       ABC

我创建了一个查询: -

select nam,control_num
from table_a a,table_b b
where sysdate between approv_begin_date(+) and approv_end_date(+)

这给了我正确的输出

nam control_num
10  1
20  

现在情况发生了变化,我也必须考虑prov_end_date以防万一批准日期为空.... 为此,我创建了以下条件

   select nam,control_num
    from table_a a,table_b b
    where sysdate between DECODE (approv_begin_date
,                NULL, a.prov_begin_date
,                a.approv_begin_date)and DECODE (approv_end_date
,                NULL, a.prov_end_date
,                a.approv_end_date)

this will just give me :
  nam control_num
    10  1

我如何在这里使用外连接?

2 个答案:

答案 0 :(得分:3)

这是建立在周四的答案。我认为查询更清晰:

select nam, control_num
from table_b b left join
     table_a a
     on b.emp_num = a.emp_num and
        sysdate between coalesce(a.approv_begin_date, a.prov_begin_date) and
                        coalesce(a.approv_end_date, a.prov_end_date);

你应该学习明确的join语法,因为它允许旧式语法不具有的连接。另外,decode()特定于Oracle(它已被弃用了吗?)。 ANSI标准方法是CASE;但是,出于您的目的,COALESCE()是正确的功能并且易于使用。

请注意sysdate有一个时间组件。你很可能真的想要:

trunc(sysdate) between coalesce(a.approv_begin_date, a.prov_begin_date) and
                             coalesce(a.approv_end_date, a.prov_end_date);

答案 1 :(得分:1)

将联接更改为类似内容会发生什么?

select nam,control_num
from table_a a
left join table_b b
  on b.emp_num = a.emp_num
where sysdate between DECODE (approv_begin_date
,                NULL, a.prov_begin_date
,                a.approv_begin_date)and DECODE (approv_end_date
,                NULL, a.prov_end_date
,                a.approv_end_date)