![](/img/trans.png)
[英]What is the most concise way of pulling database objects from a db into a list?
[英]In Postgres: What is the most concise way to use `IS DISTINCT FROM` on multiple values?
我正在尝试查找具有枚举列的所有行,该列要么是 NULL,要么与给定的一组枚举值不同。 我可以用很多IS DINSTINCT FROM
调用来做到这一点,但它真的很冗长,我宁愿使用NOT IN()
语法,但NULL
会抛弃它。
这是我想在 SQL 中做的一个例子,来自这个小提琴: http://sqlfiddle.com/#!17/dfae4d/8
CREATE TYPE mood AS ENUM ('sad', 'ok', 'happy');
CREATE TABLE people (
name text,
current_mood mood,
current_mood_as_text varchar
);
insert into people values('Mr Happy', 'happy', 'happy');
insert into people values('Mr Sad', 'sad', 'sad');
insert into people values('Mr Null', NULL, NULL);
-- This doesn't return MrUnknown because of the NULL value:
select * from people where current_mood NOT IN ('happy');
-- This works great, and includes Mr Null:
select * from people where current_mood IS DISTINCT FROM 'happy';
-- But If I want to start comparing to multiple moods, it gets more verbose fast:
SELECT * FROM people
WHERE current_mood IS DISTINCT FROM 'happy' AND
current_mood IS DISTINCT FROM 'sad';
-- You can't write this, but it's kinda what I want:
-- SELECT * FROM people
-- WHERE current_mood IS DISTINCT FROM ('happy', 'sad');
-- For the non enum column, I could do this to make my intention and code clear and concise
SELECT * FROM people
WHERE coalesce(current_mood_as_text, '') NOT IN ('happy', 'sad');
-- But if I write this, I get an error because '' is not a valid enum value
-- SELECT * FROM people
-- WHERE coalesce(current_mood, '') NOT IN ('happy', 'sad');
还有另一种方法可以使这种多重比较更简洁吗?
使用coalesce()
的解决方案:
select *
from people
where coalesce(current_mood not in ('happy', 'sad'), true)
还有一种方式:
SELECT * FROM people
WHERE NOT EXISTS (
SELECT FROM (VALUES ('happy'::mood), ('sad')) v(m)
WHERE people.current_mood = v.m
);
Cleanest(IMO) 方法是在 CTE 中使用VALUES()
并对该表表达式执行NOT EXISTS()
:
WITH m(m) AS ( VALUES( 'happy'::mood) )
SELECT *
FROM people p
WHERE NOT EXISTS (
SELECT * FROM m
WHERE m.m = p.current_mood
);
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.