1、安装pg_trgm插件
- 到postgres软件安装目录:
/home/postgres/soft/postgresql-9.6.12/contrib/pg_trgm
2、翻译安装
make USE_PGXS=1 && make USE_PGXS=1 install
3、检查安装是否成功。
ll $PGHOME/lib/pg_trgm.so
显示如下,安装成功:
-rwxr-xr-x 1 postgres postgres 53112 3月 25 10:42 /home/postgres/postgresql-9.6.12/lib/pg_trgm.so
4、创建extension
testdb=# create extension pg_trgm; CREATE EXTENSION
2、优化过程
1、准备表和测试数据。
testdb=# \dt+ t_user List of relations Schema | Name | Type | Owner | Size | Description --------+--------+-------+----------+--------+------------- public | t_user | table | postgres | 769 MB | (1 row) testdb=# select count(1) from t_user; count --------- 6000000 (1 row) testdb=#
2、优化前:
testdb=# \d+ t_user; Table "public.t_user" Column | Type | Modifiers | Storage | Stats target | Description --------+-----------------------+-----------+----------+--------------+------------- id | bigint | not null | plain | | name | character varying(50) | | extended | | email | character varying(50) | | extended | | type | integer | | plain | | iphone | character varying(13) | | extended | | Indexes: "t_user_pkey" PRIMARY KEY, btree (id) testdb=# explain ANALYZE select * from t_user where name like '%abc%'; QUERY PLAN --------------------------------------------------------------------------------------------------------------- Seq Scan on t_user (cost=0.00..173361.26 rows=600 width=99) (actual time=0.179..2261.550 rows=43722 loops=1) Filter: ((name)::text ~~ '%abc%'::text) Rows Removed by Filter: 5956278 Planning time: 0.665 ms Execution time: 2265.169 ms (5 rows) testdb=# explain ANALYZE select * from t_user where name like '%abc%'; QUERY PLAN --------------------------------------------------------------------------------------------------------------- Seq Scan on t_user (cost=0.00..173361.26 rows=600 width=99) (actual time=0.108..1494.702 rows=43722 loops=1) Filter: ((name)::text ~~ '%abc%'::text) Rows Removed by Filter: 5956278 Planning time: 0.162 ms Execution time: 1496.646 ms (5 rows)
3、创建索引,并收集统计信息:
testdb=# CREATE INDEX idx_trgm_user_name_ ON t_user USING GIN(name gin_trgm_ops); CREATE INDEX testdb=# testdb=# ANALYZE t_user; ANALYZE
4、优化后:
testdb=# explain ANALYZE select * from t_user where name like '%abc%'; QUERY PLAN ------------------------------------------------------------------------------------------------------------------------------------- Bitmap Heap Scan on t_user (cost=20.65..2283.92 rows=600 width=99) (actual time=36.398..132.911 rows=43722 loops=1) Recheck Cond: ((name)::text ~~ '%abc%'::text) Heap Blocks: exact=35367 -> Bitmap Index Scan on idx_trgm_user_name_ (cost=0.00..20.50 rows=600 width=0) (actual time=21.842..21.842 rows=43722 loops=1) Index Cond: ((name)::text ~~ '%abc%'::text) Planning time: 8.502 ms Execution time: 136.646 ms (7 rows) testdb=# explain ANALYZE select * from t_user where name like '%abc%'; QUERY PLAN ------------------------------------------------------------------------------------------------------------------------------------- Bitmap Heap Scan on t_user (cost=20.65..2283.92 rows=600 width=99) (actual time=34.787..124.970 rows=43722 loops=1) Recheck Cond: ((name)::text ~~ '%abc%'::text) Heap Blocks: exact=35367 -> Bitmap Index Scan on idx_trgm_user_name_ (cost=0.00..20.50 rows=600 width=0) (actual time=20.599..20.599 rows=43722 loops=1) Index Cond: ((name)::text ~~ '%abc%'::text) Planning time: 0.214 ms Execution time: 128.587 ms (7 rows)
结论:
没有创建索引时。查询需要2秒左右。优化后只需要0.1秒。相差20倍