PostgreSQL的。按数组字段值的交集过滤

时间:2016-09-30 14:59:59

标签: sql postgresql

我的数据集是:

# select * from test;
   list   | locked
 ---------+--------
  {a,b,c} | t
  {f,g,h} | f
  {c,d,e} | f

我需要选择locked = FALSE行,列表值不与任何locked = TRUE行相交。

到现在为止,我坚持:

# SELECT * FROM test WHERE NOT locked and NOT list && (SELECT list FROM test WHERE locked);
  list   | locked
---------+--------
 {f,g,h} | f
 (1 row)

工作但通过比较每个locked = TRUE行看起来过头了。我正在寻找一种方法来选择所有locked = TRUE列表值的聚合集合,并为每个locked = FALSE行比较一次。

1 个答案:

答案 0 :(得分:1)

您的查询应该可以正常运行。如果我理解正确,你正在寻找更高效的东西。如果你愿意创建一个新表,你可以这样:

CREATE TABLE locked(elem text PRIMARY KEY);
INSERT INTO locked SELECT DISTINCT unnest(list) FROM test WHERE locked;

此表将包含test中与锁定状态对应的所有列表中的所有元素。我正在使用unnest函数将text[]转换为text表格,以便我可以应用DISTINCT

然后你会像那样使用那个表

SELECT *
FROM test
WHERE NOT locked AND
      NOT exists(SELECT FROM locked WHERE elem=ANY (list));

请注意,上次查询中的NOT locked条件是多余的,但如果您使用它,可能会提高性能。

如果您需要更好的性能,则可能需要进一步规范表test