PostgreSQL。按数组字段值的交集过滤
Posted
技术标签:
【中文标题】PostgreSQL。按数组字段值的交集过滤【英文标题】:postgresql. filter by intersection of array field values 【发布时间】:2016-09-30 14:59:58 【问题描述】:我的数据集是:
# select * from test;
list | locked
---------+--------
a,b,c | t
f,g,h | f
c,d,e | f
我需要选择列表值不与任何locked=TRUE 行相交的locked=FALSE 行。
到现在为止,我被困住了:
# 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】:您的查询应该可以正常工作。如果我对您的理解正确,那么您正在寻找更有效的东西。如果你愿意创建一个新表,你可以这样:
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
。
【讨论】:
这是个好建议。但 ti 不满足我的需求。锁机制意味着并发。我的表应该作为作业队列工作,其中并发工作者通过设置锁定属性和 RETURNING * 的 UPDATE 行获取作业,因此其他工作者不能接受它。在这种情况下,管理单独的锁表比比较每一行的开销要大得多。以上是关于PostgreSQL。按数组字段值的交集过滤的主要内容,如果未能解决你的问题,请参考以下文章