使用PostgreSQL在SQL查询中创建空数组,而不是内部为NULL的数组
我正在使用以下模式:使用PostgreSQL在SQL查询中创建空数组,而不是内部为NULL的数组,sql,arrays,postgresql,Sql,Arrays,Postgresql,我正在使用以下模式: CREATE TABLE person ( person_name VARCHAR PRIMARY KEY ); CREATE TABLE pet ( animal_name VARCHAR, person_name VARCHAR REFERENCES person(person_name), PRIMARY KEY (animal_name, person_name) ); 我希望创建一个表,其中,对于每个人名,我将获得一个包含该人宠物的数组。我正在
CREATE TABLE person (
person_name VARCHAR PRIMARY KEY
);
CREATE TABLE pet (
animal_name VARCHAR,
person_name VARCHAR REFERENCES person(person_name),
PRIMARY KEY (animal_name, person_name)
);
我希望创建一个表,其中,对于每个人名
,我将获得一个包含该人宠物的数组。我正在使用PostgreSQL 9.3.4
我在每个表中都有以下值:
人
PERSON_NAME
-----------
Alice
Bob
宠物
ANIMAL_NAME | PERSON_NAME
-------------------------
Woof | Alice
Meow | Alice
我希望创建下表:
PERSON_NAME | PETS
--------------------------
Alice | {Woof, Meow}
Bob | {}
但是,我无法创建空数组。我得到的是:
PERSON_NAME | PETS
--------------------------
Alice | {Woof, Meow}
Bob | {NULL}
这是我正在使用的查询:
SELECT
person.person_name,
array_agg(pet.animal_name) AS pets
FROM
person LEFT JOIN pet ON person.person_name = pet.person_name
GROUP BY
person.person_name
;
我明白为什么我得到的数组里面有NULL
值,我想知道如何得到一个空数组
下面是一个示例,其中包含创建模式、插入值和使用的查询所需的代码。网站中显示的结果没有显示NULL
值,尽管它存在
编辑
结果将被解析为JSON,这就是为什么
{NULL}
不是可接受的结果,因为它将被解析为[NULL]
,这与我需要的[]
不同。出于同样的原因,类似于{”“}
的结果也是不可接受的。您可以使用合并
替换空值
值:
SELECT
person.person_name,
array_agg(coalesce(pet.animal_name,'')) AS pets
FROM
person LEFT JOIN pet ON person.person_name = pet.person_name
GROUP BY
person.person_name
;
我想到了两种可能性 一个选择是联合
select person.person_name, array_agg(pet.animal_name) as pets
from person
join pet on person.person_name = pet.person_name
group by person.person_name
union
select person.person_name, array[]::text[] as pets
from person
left join pet on person.person_name = pet.person_name
where pet.animal_name is null
第一部分使用连接来获得有宠物的人,然后第二部分抓住那些根本没有宠物的穷人。分离它们可以为没有宠物的人提供一个文本空数组
另一种选择是使用派生表的左连接执行几乎相同的操作:
with pet_names as (
select person.person_name, array_agg(pet.animal_name) as pets
from person
join pet on person.person_name = pet.person_name
group by person.person_name
)
select p.person_name, coalesce(n.pets, array[]::text[])
from person p
left join pet_names n on p.person_name = n.person_name
这对我来说更自然一些,因为它允许您使用COALESCE(您想要将NULL映射到其他对象的第一件事情)来提供空数组
更新的演示:
可能还有其他解决方案,这两种方法对我来说似乎是很自然的方法。最简单的方法是使用:
我只想补充一点,这已经6岁了 数组[]:::varchar[]
这给了我
{”“}
而不是{}
。我相信它们不一样。@9lo--除了NULL
和空字符串之外,我不知道还有其他值。您可能在谈论表示逻辑而不是sql。这是上述查询的结果——通过终端在psql中检查结果。我确实说过fiddle中显示的结果不会打印NULL
值。查询得到的结果将被解析为JSON,其中[]!=[null]
以及[]!=[“”]
。我很抱歉更改了公认的答案,但是@pozs的答案看起来更干净。
SELECT
person.person_name,
ARRAY(SELECT animal_name FROM pet WHERE person.person_name = pet.person_name) AS pets
FROM
person;