2017-07-19 111 views
0

我有一列我想根据某些条件从结果集中筛选出的行。目前,它看起来像这样在我的查询:Postgres:否定CASE语句中的条件

WHERE col1 = 'x' OR col1 ~~ '%y%' AND col2 = 'z' ... 

现在我要为大家介绍的是文档的某些行被过滤掉的原因一个新列:

SELECT ... 
    , CASE WHEN condition1 THEN 'Exclusion Reason 1' 
     WHEN condition2 THEN 'Exclusion Reason 2' 
     ... 
     ELSE '' 
    END AS exclusion_reason 

的问题:它似乎没有在上班的路上我使用的否定:

SELECT ... 
    , CASE WHEN condition1 THEN 'Reason 1' 
     WHEN condition2 THEN 'Reason 2' 
     WHEN NOT (col1 = 'x' OR col1 ~~ '%y%' AND col2 = 'z'...) THEN 'Reason 3' 
     ELSE '' 
    END AS exclusion_reason 

它不Reason 3返回任何行,但它应该。离开了NOT标志着中行的子集:

SELECT ... 
    , CASE WHEN condition1 THEN 'Reason 1' 
     WHEN condition2 THEN 'Reason 2' 
     WHEN (col1 = 'x' OR col1 ~~ '%y%' AND col2 = 'z'...) THEN 'Not Reason 3' 
     ELSE '' 
    END AS exclusion_reason 

为什么如预期的,什么是在这里使用正确的语法并不否定不行?

+0

仅供[文档](https://www.postgresql.org/docs/9.1/static/sql-expressions.html#SYNTAX-EXPRESS-EVAL)明确表示的评论:*“评估顺序的子表达式没有被定义,特别是,操作符或函数的输入不一定是从左到右或以任何其他固定顺序进行评估。“*,那么用'()'围绕就更安全了。比赛。在给出的例子中,((col1 ='x'或col1 ~~'%y%')AND col2 ...)等 –

回答

1

我要去猜测,原因是NULL值,所以是这样的:

WHEN NOT (col1 = 'x' OR col1 ~~ '%y%' AND col2 = 'z'...) OR col1 IS NULL THEN 'Reason 3' 

在条件为A NULL值将返回NULLNOT NULL仍然是NULL - 这被视为虚假。