Postgres GIST vs Btree指数

kap*_*pso 15 postgresql postgis

继我之前关于此主题的问题后,Postgres结合了多个索引:

我在Postgres 9.2(带postgis)上有下表:

CREATE TABLE updates (
    update_id character varying(50) NOT NULL,
    coords geography(Point,4326) NOT NULL,
    user_id character varying(50) NOT NULL,
    created_at timestamp without time zone NOT NULL
);
Run Code Online (Sandbox Code Playgroud)

我在桌子上运行以下查询:

select * 
from updates 
where ST_DWithin(coords, ST_MakePoint(-126.4, 45.32)::geography, 30000) 
and user_id='3212312' 
order by created_at desc
limit 60
Run Code Online (Sandbox Code Playgroud)

那么,我应该使用什么索引(coords + user_id),GIST或BTree?

CREATE INDEX ix_coords_user_id ON updates USING GIST (coords, user_id);
Run Code Online (Sandbox Code Playgroud)

要么

CREATE INDEX ix_coords_user_id ON updates (coords, user_id);
Run Code Online (Sandbox Code Playgroud)

我在读BTree的表现比GIST好,但是因为我使用postgis地理领域,我被迫使用GIST?

Cra*_*ger 12

如果要使用除常规b树索引(或哈希索引之外的任何索引方法,但不应该使用它们),则必须使用GiST.PostGIS索引需要GiST.

B-tree索引只能用于涉及平等和排序的基本操作,如=,<,<=,>,>=,<>,BETWEENIN.虽然您可以在地理对象(点,区域等)上创建b树索引,但它实际上只能用于相等,因为>对这些对象通常没有意义的排序比较.需要GiST索引来支持更复杂和一般的比较,如"包含","相交"等.

您可以使用该btree_gist扩展为GiST启用b-tree索引.它比常规的B树索引要慢得多,但允许您创建包含仅GiST的类型和常规类型,如多列索引text,integer等等.


在这些情况下,您确实需要使用explain analyze(explain.depesz.com对此有用)来检查Pg如何使用您创建的各种索引和索引组合.在多列索引中尝试不同的列顺序,并查看两个或更多单独的索引是否更有效.

我强烈怀疑在这种情况下你会用多列GiST索引获得最佳结果,但我会尝试几种不同的索引和索引列排序组合来查看.

  • @ user310525仅仅因为你可以创建索引并不意味着它正在为你做任何有用的事情.检查`explain analyze`输出以查看使用哪些索引以及如何使用.B树索引只能用于`=`,`<`,`<=`,`>`,`> =`,`<>`和`BETWEEN` - 所以很可能它没有做任何擅长所有对于PostGIS部分的查询,你最好在`(user_id)`上使用单列b-tree索引. (2认同)