2016-07-14 23 views
0

我有我的功能與一個參數carAzimuth如何使用參數/變量和一起解釋

CREATE OR REPLACE FUNCTION map.get_near_link(x numeric, y numeric, carAzimuth numeric) 

裏面我有一些計算和這個查詢

SELECT * 
FROM map.vzla_seg S 
WHERE 
    S.azimuth > carAzimuth - 30 and 
    S.azimuth < carAzimuth + 30 or 
    S.azimuth < carAzimuth - 330 or 
    S.azimuth > carAzimuth + 330; 

我想分析查詢服務表現。所以我必須替換一個常量的變量。並且工作正常,並且EXPLAIN PLAN顯示我正在使用正確的索引。

EXPLAIN ANALYZE  
SELECT * 
FROM map.vzla_seg S 
WHERE 
    S.azimuth > 345 - 30 and 
    S.azimuth < 345 + 30 or 
    S.azimuth < 345 - 330 or 
    S.azimuth > 345 + 330; 

但是如果要測試不同的值,麻煩更改每個變量。然後,如果你嘗試

EXPLAIN ANALYZE 
    WITH param(carAzimuth) as (select 345) 
    SELECT * 
    FROM vzla_seg S, param 
    WHERE 
     S.azimuth > carAzimuth- 30 and 
     S.azimuth < carAzimuth + 30 or 
     S.azimuth < carAzimuth - 330 or 
     S.azimuth > carAzimuth + 330; 

作品,但停止使用FULL SCAN

"Nested Loop (cost=0.01..208990.91 rows=2328905 width=4) (actual time=0.146..4138.882 rows=642115 loops=1)" 
" Join Filter: (((s.azimuth > (p.carazimuth - 30)) AND (s.azimuth < (p.carazimuth + 30))) OR (s.azimuth < (p.carazimuth - 330)) OR (s.azimuth > (p.carazimuth + 330)))" 
" Rows Removed by Join Filter: 3207719" 
" CTE parameter" 
" -> Result (cost=0.00..0.01 rows=1 width=0) (actual time=0.002..0.002 rows=1 loops=1)" 
" -> CTE Scan on parameter p (cost=0.00..0.02 rows=1 width=4) (actual time=0.009..0.012 rows=1 loops=1)" 
" -> Seq Scan on vzla_seg s (cost=0.00..93496.22 rows=3849822 width=4) (actual time=0.072..1380.356 rows=3849834 loops=1)" 
"Total runtime: 4253.113 ms" 

指數和變化那麼,有沒有辦法,我可以創造我的變量和使用它的解釋,而不必一個功能?

我使用pgAdmin上的SQL編輯器來運行我的查詢。

回答

3

你假設所以WITH子句是等價函數是錯誤的。子句WITHCommon Table Expressions有關,並且與函數的關係爲零。當你將看到從功能規劃,有兩種可能性:

  1. 使用auto_explain延伸 - 與此擴展可以登錄任何嵌套的計劃 - 只要啓用選項auto_explain.log_nested_statements

  2. 可以使用準備好的語句 - 任何SQL都可以透明地轉換爲PLpgSQL中的預處理語句。

    prepare xx(int) as select * from foo where a = $1::text; 
    explain analyze execute xx(10); 
    ┌───────────────────────────────────────────────────────────────────────────────────────────────┐ 
    │           QUERY PLAN           │ 
    ╞═══════════════════════════════════════════════════════════════════════════════════════════════╡ 
    │ Seq Scan on foo (cost=0.00..21.00 rows=4 width=64) (actual time=0.019..0.019 rows=0 loops=1) │ 
    │ Filter: (a = '10'::text)                 │ 
    │ Rows Removed by Filter: 2                 │ 
    │ Execution time: 0.052 ms                  │ 
    └───────────────────────────────────────────────────────────────────────────────────────────────┘ 
    

    注意:前5次執行計劃總是新鮮的(不重複使用,並且會一次又一次地生成)。 5次執行後,該計劃可以是通用的並且可以重複使用。請參閱related documentation中的計劃緩存章節。

+0

第二個選項看起來不錯,我試了一下,但把解釋計劃作爲第一行,並沒有工作。現在將檢查嵌套的計劃。 –

+0

我嘗試鏈接中的'auto_explain'示例,並沒有發生任何事情。我將每個變量設置爲true,任何想法我缺少什麼? –

+0

你檢查過postgresql日誌嗎?你重新啓動postgres(如果你通過shared_preload_libraries加載auto_explain)? –

相關問題