sql 查询带撇号 (') 的 NVL 字符串

sql query NVL string with apostrophes (')

所以我有一个 sql 我目前正在处理的查询是这样的:

SELECT * from tableA where 
( status = NVL('','OPEN') or status = NVL('','CLOSED') )
and delete_flag != 'Y'

上面的查询工作正常并给了我想要的结果..但我想知道是否可以将上面的 status IN NVL 行合并为一个而不是使用 or there。

例如,我希望能够做到:

SELECT * from tableA where 
status IN NVL('','OPEN','CLOSED')
and delete_flag != 'Y'

但是这里的撇号不适合我..我该如何解决它?

您正在从您的应用程序中获取一个输入参数,该参数的值可以是 "Open"、"Closed" 或 null

您希望能够 select 状态值等于此输入参数(如果它为空)或输入值(如果它不是)。

要使筛选器默认为空值,您可以使用 COALESCE 和要筛选的列。

像这样

SELECT * from tableA
where COALESCE(parameter,status) = status
  and status in ('OPEN','CLOSED') -- see comments
  and delete_flag != 'Y'

在这种情况下,如果参数为 OPEN,您将获得所有打开的项目,如果参数为 CLOSED,您将获得所有关闭的项目,如果参数为空,您将获得所有项目。

这是 Web 应用程序中非常常见的模式。


单行版本

SELECT * from tableA
where COALESCE(parameter,CASE WHEN status in ('OPEN','CLOSED') then status ELSE '' END) = status
  and delete_flag != 'Y'

简单地说:

SELECT * from tableA 
 where 1=1
   and  nvl(status, '---') IN ('OPEN','CLOSED') 
   and delete_flag != 'Y'

在 Oracle 中,空字符串 '' 等同于 NULL.

所以 NVL( '', 'OPEN' ) 等价于 NVL( NULL, 'OPEN' ) 可以简化为 'OPEN'.

所以您的查询是:

SELECT *
FROM   tableA
WHERE  ( status = 'OPEN' OR status = 'CLOSED' )
AND    delete_flag != 'Y'

可以简化为:

SELECT *
FROM   tableA
WHERE  status IN ( 'OPEN', 'CLOSED' )
AND    delete_flag != 'Y'

您可以使用集合实现动态选项列表:

CREATE TYPE stringlist IS TABLE OF VARCHAR2(100);
/

SELECT a.*
FROM   tableA a
       INNER JOIN
       ( SELECT stringlist( 'OPEN', 'CLOSED' ) AS options FROM DUAL ) o
       ON ( o.options IS EMPTY OR a.status MEMBER OF o.options )
WHERE  a.delete_flag <> 'Y'