【问题标题】:SQL - CASE statement in filter with optional useSQL - 过滤器中的 CASE 语句,可选使用
【发布时间】:2015-12-16 23:37:29
【问题描述】:

对不起,我没有更好的词来为我的问题命名,但基本上我正在寻找过滤条件中 CASE/AND...OR 语句的实现,如果特定 ID 的值不是 NULL 并且大于0,则只考虑该 ID 的条件,否则根本不需要使用该 ID 的条件。

示例 1:

    select emp_id, cust_id, date_id
    from employee a
    join customer l
    on a.id = l.id
    join time_table ACT
    on a.join_date_id = ACT.date_id
    where a.emp_id = 1
    and l.cust_id in (2, 3)
    and ACT.date_id >= to_char((sysdate - EXTRACT(DAY FROM (SYSDATE))) - 90, 'DD-MON-YYYY')
    and ACT.date_id <= to_char(sysdate -  EXTRACT(DAY FROM (SYSDATE)), 'DD-MON-YYYY')
    and a.sub_emp_id = CASE WHEN @sub_emp_id IS NOT NULL AND @sub_emp_id > 0 THEN @sub_emp_id WHEN @sub_emp_id IS NULL THEN @sub_emp_id ELSE @sub_emp_id END -- where condition is, if sub_emp_id is not null and if sub_emp_id > 0 then use the value of sub_emp_id otherwise if sub_emp_id is NULL, then don't use the condition for sub_emp_id altogether.

示例 2 -

    select emp_id, cust_id, date_id
    from employee a
    join customer l
    on a.id = l.id
    join time_table ACT
    on a.join_date_id = ACT.date_id
    where (a.emp_id = 1
    and l.cust_id in (2, 3)
    and ACT.date_id >= to_char((sysdate - EXTRACT(DAY FROM (SYSDATE))) - 90, 'DD-MON-YYYY')
    and ACT.date_id <= to_char(sysdate -  EXTRACT(DAY FROM (SYSDATE)), 'DD-MON-YYYY')
    and a.sub_emp_id > 0)
    OR
    (a.emp_id = 1
    and l.cust_id in (2, 3)
    and ACT.date_id >= to_char((sysdate - EXTRACT(DAY FROM (SYSDATE))) - 90, 'DD-MON-YYYY')
    and ACT.date_id <= to_char(sysdate -  EXTRACT(DAY FROM (SYSDATE)), 'DD-MON-YYYY')) -- where condition is, "if sub_emp_id is not null and if sub_emp_id > 0" then use the value of sub_emp_id otherwise "if sub_emp_id is NULL, then don't use the condition for sub_emp_id altogether".

【问题讨论】:

  • 好的..那么你到底在哪里面临问题?
  • 对不起@avi 的困惑,我实际上是在寻找最有效的查询,我相信我之前的两种方法不是这样工作的。

标签: sql oracle case where


【解决方案1】:

我认为你是为此而拍摄的:

case
    when @sub_emp_id > 0 /* not null is also implied */
    then case when a.sub_emp_id = @sub_emp_id then 1 else 0 end
    else 1
end = 1

我认为这些是等效的选择:

not (@sub_emp_id > 0 and a.sub_emp_id <> @sub_emp_id)
coalesce(@sub_emp_id, 0) <= 0 or a.sub_emp_id = @sub_emp_id

【讨论】:

    【解决方案2】:

    如果我理解正确,您会希望sub_emp_id 上的过滤器看起来像这样:

    ...
    and (@sub_emp_id is null or
         @sub_emp_id <= 0 or
         a.sub_temp_id = @sub_emp_id)
    

    【讨论】:

      【解决方案3】:

      您通常需要对“全部”进行空匹配。简单的模式是这样的:

      WHERE coalesce(@sub_emp_id, a.sub_temp_id) = a.sub_temp_id
      

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2020-09-02
        • 2015-02-11
        • 1970-01-01
        • 2011-10-08
        • 1970-01-01
        相关资源
        最近更新 更多