当前位置: 首页 > 面试题库 >

带索引的Postgres查询计划

怀飞掣
2023-03-14
问题内容

我有一个具有以下架构的postgres表

     Table "public.myTable"
  Column               |           Type           | Modifiers 
-----------             +--------------------------+-----------
 serial_number         | character varying(255)   | 
 name                  | character varying(255)   | 
 Designation           | character varying(255)   | 
 place                 | character varying(255)   | 
 timeOfJoining         | timestamp with time zone | 
 timeOfLeaving               | timestamp with time zone |

Indexes:
    "name_Designation_place" btree (name, Designation, place)
    "Designation_place_name" btree (Designation, place, name)
    "Designation_name_place" btree (Designation, name, place)
    "timeOfJoining_timeOfLeaving" btree (timeOfJoining, timeOfLeaving)
    "timeOfJoining_timeOfLeaving" btree (timeOfJoining, timeOfLeaving)

现在,当我运行表单查询时:

explain analyze select place from myTable where Designation='Manager' and timeOfJoining>'1930-10-10';

我正在制定以下计划:

Index Scan using Designation_place_name on myTable  (cost=0.00..67701.36 rows=22043 width=27) (actual time=0.061..3.796 rows=3376 loops=1)
   Index Cond: ((relation)::text = 'Manager'::text)
   Filter: (timeOfJoining > '1930-10-10 00:00:00+05:53:20'::timestamp with time zone)
 Total runtime: 4.082 ms
(4 rows)

现在,我无法理解查询计划的执行方式。查询计划是否首先从myTable的索引Designation_place_name检索序列号,然后转到myTable并获取行,然后对timeOfJoining执行过滤

或者

查询计划是否同时获取索引timeOfJoining_timeOfLeaving和Designation_place_name,然后执行联接,并且在此联接上进行了过滤?


问题答案:

该计划:

Index Scan using Designation_place_name on myTable  (cost=0.00..67701.36 rows=22043 width=27) (actual time=0.061..3.796 rows=3376 loops=1)
   Index Cond: ((relation)::text = 'Manager'::text)
   Filter: (timeOfJoining > '1930-10-10 00:00:00+05:53:20'::timestamp with time zone)
 Total runtime: 4.082 ms
(4 rows)

基本上是指:

  1. 使用Designation_place_name索引
  2. 查找符合索引条件关系=“经理”的行
  3. 仅保留符合timeOfJoining条件的行

在第2步中,磁盘页是“随机”访问的,而不是顺序访问的,也就是说,索引包含磁盘上匹配行的地址,而Postgres则按照索引指示的顺序访问这些地址。(顺便说一句,这可能会很昂贵。有时,计划者会决定便宜一点,即只读取整个表(seq扫描)或批量获取页面上的所有行,而忽略索引指示的顺序(位图索引扫描)。)

注意:该查询中没有(表)联接。如果有一个,您会看到额外的缩进级别。从缩进到缩进的顺序阅读它们。



 类似资料:
  • 问题内容: 我有几个查询,其中大多数是: 和 由于它们都是一个范围,因此在col和date上使用未聚类的b +树索引会是加快查询速度的一个好主意吗?还是哈希索引?还是没有索引会更好? 问题答案: 在 过滤谓词上 用作 日期范围条件 的列上创建 INDEX 应该很有用,因为它将执行 INDEX RANGE SCAN 。 这是有关如何在Oracle中创建,显示和阅读EXPLAIN PLAN 的演示。

  • 问题内容: 我有2张表,如下所示: 当我解释查询时: postgres给我这个: 过了一会儿给我这个完全相同的查询(仍然不使用索引): 我的问题是:如果我仅按构成唯一索引的st值和类型值进行过滤,为什么不使用此唯一索引? 问题答案: 您的表没有足够的行来使用索引。它们适合放在单个磁盘页面中,因此使用cpu时间读取整个内容并筛选出行要比两次执行同​​一操作(一次用于索引,另一次用于数据)要快。

  • 我刚加入弹性搜索公司。而不知道如何在JSON请求中对索引和an类型发出正确的请求?(所以我不想像localhost:9200/myindex/mytype/_search那样在URL中使用索引和类型,而是向localhost:9200/_search发出JSON请求) 我试过这样的东西。但我得到的结果是'AAA'索引而不是'BBB'索引。如何只从bbb索引得到结果或者根本没有结果?

  • 问题内容: 我似乎找不到太多的文档。在支持这种查询的PostgreSQL上创建数据库/表的最简单方法是什么?SELECT * FROM table WHERE distance(POINT(0,0),table.location)<= 1000m; 其中POINT(0,0)和table.location应该是经度/纬度对,并且1000m是1000米。我应该如何索引该表?谢谢。 问题答案: Post

  • 在我的一个项目中,我有一个表,其中保存了某种设备的固件更新信息。最初,任何固件更新进程都处于排队状态。更新过程可能有其他状态值,例如正在进行、已完成、失败。对于单个设备,可能存在状态为“已完成”和“已失败”的多行(已完成的更新过程,最终状态!)。但在任何时候,处于排队或正在进行状态的每个设备都必须只有一个更新过程——新固件的推出应该只适用于没有“活动/非最终”更新过程的设备。我试图用Postgre

  • 问题内容: 如何在Elasticsearch中按数组索引查询/过滤? 我有一个像这样的文件: 我想搜索 LIN [0] 是否为“ UP”并且 LIN [1]是否 存在。 谢谢。 问题答案: 这看起来可能像hack,但是可以肯定地起作用。首先,我们将令牌计数类型与多字段一起应用以捕获令牌数量作为字段。因此,映射将如下所示- 链接-http: //www.elasticsearch.org/guide