【发布时间】:2020-04-17 10:26:01
【问题描述】:
Postgres 版本:9.5.19
我有下表包含域:
CREATE TABLE sites (
id SERIAL PRIMARY KEY,
domain character varying(255),
);
-- Indices -------------------------------------------------------
CREATE UNIQUE INDEX sites_pkey ON sites(id int4_ops);
CREATE INDEX index_sites_on_domain ON sites(domain text_ops);
id | domain
---| -----------
1 | www.abc.com
2 | alpha.net
3 | catfood.xyz
4 | example.org
5 | un.gov
6 | xyz.com
. | .......
表中的记录总数接近 100 万条,运行模式匹配查询轻松需要 20 多秒:
SELECT * from sites where domain LIKE '%abc.com%
我在domain 上有一个正常的btree 索引,但上面的查询没有使用它。 EXPLAIN 显示顺序扫描。
如何索引此列以使查询得到充分优化?
【问题讨论】:
-
Like '%xxx%' 不使用 btree 索引。就像 'xxx%' 一样。考虑使用 pg_trgm,如下所述:postgresql.org/docs/9.5/pgtrgm.html
-
您的表是命名为“sites”,还是命名为“domains”?
-
该查询对我来说很容易在半秒内完成(针对站点,而不是域),没有 1,572,864 行的索引。 '%un%' 太短,无法从三元组索引中受益,所以如果这是一个有代表性的查询,它不会对你有多大好处。
-
在查询中使用正确的表名更新了问题。我同意 %un% 太短,但是,我们使用的实际通配符模式比这长,主要是实际域,例如www.abc.com、www.longls.com 等等等等。
-
我同意 jjanes:20 秒对一百万行进行全表扫描似乎相当慢。但如果您的搜索模式较长,则三元组索引可能会有所帮助
标签: postgresql indexing pattern-matching query-optimization sql-like