查询计划中执行时间部分的差距

Gap in the execution-time parts in the query plan

我无法理解以下查询计划(匿名)。查询的实际部分花费的时间似乎存在差距,并且缺少一部分。

相关部分:

->  Sort  (cost=306952.44..307710.96 rows=303409 width=40) (actual time=4222.122..4400.534 rows=582081 loops=1)
      Sort Key: table1.column3, table1.column2
      Sort Method: quicksort  Memory: 71708kB
      Buffers: shared hit=38058
      ->  Index Scan using myindex on table1  (cost=0.56..279325.68 rows=303409 width=40) (actual time=0.056..339.565 rows=582081 loops=1)
            Index Cond: (((column1)::text = 'xxx1'::text) AND ((column2)::text > 'xxx2'::text) AND ((column2)::text < 'xxx3'::text))
            Buffers: shared hit=38058

索引扫描(直到 339.565)和开始对结果排序(4222.122)之间发生了什么?

完整计划(以防万一):

GroupAggregate  (cost=344290.95..348368.01 rows=30341 width=65) (actual time=4933.739..4933.806 rows=11 loops=1)
  Group Key: t.column1, t.current_value, t.previous_value
  Buffers: shared hit=38058
  ->  Sort  (cost=344290.95..345045.68 rows=301892 width=72) (actual time=4933.712..4933.719 rows=58 loops=1)
        Sort Key: t.column1, t.current_value, t.previous_value
        Sort Method: quicksort  Memory: 32kB
        Buffers: shared hit=38058
        ->  Subquery Scan on t  (cost=306952.44..316813.23 rows=301892 width=72) (actual time=4573.523..4933.607 rows=58 loops=1)
              Filter: ((t.current_value)::text <> (t.previous_value)::text)
              Rows Removed by Filter: 582023
              Buffers: shared hit=38058
              ->  WindowAgg  (cost=306952.44..313020.62 rows=303409 width=72) (actual time=4222.144..4859.579 rows=582081 loops=1)
                    Buffers: shared hit=38058
                    ->  Sort  (cost=306952.44..307710.96 rows=303409 width=40) (actual time=4222.122..4400.534 rows=582081 loops=1)
                          Sort Key: table1.column3, table1.column2
                          Sort Method: quicksort  Memory: 71708kB
                          Buffers: shared hit=38058
                          ->  Index Scan using myindex on table1  (cost=0.56..279325.68 rows=303409 width=40) (actual time=0.056..339.565 rows=582081 loops=1)
                                Index Cond: (((column1)::text = 'xxx1'::text) AND ((column2)::text > 'xxx2'::text) AND ((column2)::text < 'xxx3'::text))
                                Buffers: shared hit=38058
Planning Time: 0.405 ms
Execution Time: 4941.003 ms

costactual time 数据在这些计划中都显示为两个数字。首先是设置时间。草率地描述,这是查询步骤传递其第一行所花费的时间。参见 this。第二个是完成时间,或最后一行的时间。

actual time=setup...completion

排序步骤中的 设置 包括检索需要排序的结果集和实际执行排序所需的时间:在 RAM 中随机排列行或希望不随机排列磁盘。 (因为快速排序通常复杂度为 O(n log(n)),对于大结果集来说可能会很长。你知道的。)

在您的计划中,内部排序处理来自索引扫描的近 60 万行。这是排序需要时间的步骤。它使用了 71,708 KB 的 RAM。

据我所知,你的计划没有任何异常。如何加快那种?您可能会尝试更短或固定长度的 column2column3 数据类型,但这都是猜测,没有看到您的查询和 table 定义。