PostgreSQL 中的 Gist 索引仅适用于顺序,但不适用于谓词
Gist index in PostgreSQL only works on order, but not on where predicate
我有一个带有 LatLon
的普通 table 列,其中包含一个对象位置在 space 中的点,并在 GiST 上创建了索引本栏目:
create table "Machine"
(
"MachineId" integer not null,
"Name" text,
"Description" text default ''::text,
"LatLon" point default point((0)::double precision, (0)::double precision) not null
);
create index on "Machine" using gist("LatLon");
我有一个关于只选择距离固定坐标点一定距离内的点的查询:
select * from "Machine" where "LatLon" <-> point(25.123456789,-60.123456789) < 100;
尽管对此类查询的解释显示在执行期间未使用索引:
Seq Scan on "Machine" (cost=0.00..244762.46 rows=1753121 width=208)
Filter: (("LatLon" <-> '(25.123456789,-60.123456789)'::point) < '100'::double precision)
Rows Removed by Filter: 5259364
同时,对 LatLon
列执行规范 order by
查询显示索引完美运行:
select * from "Machine" order by "LatLon" <-> point(25.123456789,-60.123456789);
Index Scan using "Machine_LatLon_idx" on "Machine" (cost=0.41..1021907.70 rows=5259364 width=216)
Order By: ("LatLon" <-> '(25.123456789,-60.123456789)'::point)
为什么 GiST 索引不适用于带有距离运算符 <->
的 where
语句?
因为有人实现了一个,而不是另一个。
请注意,这不仅仅是一个运算符,而且其他运算符对(<->
和 <
,此处)也没有使用索引。因此,您将不得不引入支持此类索引的基础架构以及此特定实现。
如果你只是想要有索引的接近的东西,你需要将距离拉入点以获得一个圆。然后你有一个很好的二元运算符来抓取索引:
select * from "Machine" where "LatLon" <@ circle(point(25.123456789,-60.123456789),100);
我有一个带有 LatLon
的普通 table 列,其中包含一个对象位置在 space 中的点,并在 GiST 上创建了索引本栏目:
create table "Machine"
(
"MachineId" integer not null,
"Name" text,
"Description" text default ''::text,
"LatLon" point default point((0)::double precision, (0)::double precision) not null
);
create index on "Machine" using gist("LatLon");
我有一个关于只选择距离固定坐标点一定距离内的点的查询:
select * from "Machine" where "LatLon" <-> point(25.123456789,-60.123456789) < 100;
尽管对此类查询的解释显示在执行期间未使用索引:
Seq Scan on "Machine" (cost=0.00..244762.46 rows=1753121 width=208)
Filter: (("LatLon" <-> '(25.123456789,-60.123456789)'::point) < '100'::double precision)
Rows Removed by Filter: 5259364
同时,对 LatLon
列执行规范 order by
查询显示索引完美运行:
select * from "Machine" order by "LatLon" <-> point(25.123456789,-60.123456789);
Index Scan using "Machine_LatLon_idx" on "Machine" (cost=0.41..1021907.70 rows=5259364 width=216)
Order By: ("LatLon" <-> '(25.123456789,-60.123456789)'::point)
为什么 GiST 索引不适用于带有距离运算符 <->
的 where
语句?
因为有人实现了一个,而不是另一个。
请注意,这不仅仅是一个运算符,而且其他运算符对(<->
和 <
,此处)也没有使用索引。因此,您将不得不引入支持此类索引的基础架构以及此特定实现。
如果你只是想要有索引的接近的东西,你需要将距离拉入点以获得一个圆。然后你有一个很好的二元运算符来抓取索引:
select * from "Machine" where "LatLon" <@ circle(point(25.123456789,-60.123456789),100);