在同一查询中运行包含NOT 'some string' = ANY(array_column)
和ORDER BY
语句的查询时,似乎有一个奇怪的性能损失。
以下是一个简化的表结构,说明了tagger
是一个UUID数组(v4)的行为:
CREATE TABLE IF NOT EXISTS "doc"."test" (
"id" STRING,
"last_active" TIMESTAMP,
"taggers" ARRAY(STRING)
)
taggers
数组可能会增长一些,可能有数百个,有时会有数千个单独的字符串。
以下查询都非常高效,并在.03秒内解决:
SELECT id FROM test ORDER BY last_active DESC LIMIT 10;
SELECT id FROM test WHERE NOT ('da10187a-408d-4dfc-ae46-857fd23a574a' = ANY(taggers)) LIMIT 10;
SELECT id FROM test WHERE ('da10187a-408d-4dfc-ae46-857fd23a574a' = ANY(taggers)) ORDER BY last_active DESC LIMIT 10;
但是,在查询中包含两个部分会跳到大约2-3秒:
SELECT id FROM test WHERE NOT ('da10187a-408d-4dfc-ae46-857fd23a574a' = ANY(taggers)) ORDER BY last_active LIMIT 10;
奇怪的是,上一个快速运行的查询列表中的最后一个查询列表几乎与慢速查询完全相同,只是没有否定。 ANY
的否定也非常快。只有当在一个限制的组合中否定ANY时,事情就会变慢。任何帮助将不胜感激。
答案 0 :(得分:1)
仅使用ORDER BY的查询不会应用任何过滤,当然会更快。
仅具有过滤NOT ... ANY()而没有ORDER BY的查询仅将过滤器应用于少量记录,直到达到LIMIT编号(在这种情况下为10)。
最后一个查询(使用NOT& ANY和ORDER BY过滤)要慢得多,因为它必须做更多的工作:它必须对表的所有记录应用过滤器,然后对它们进行排序,最后返回第一个10(限制)。