2017-02-16 61 views
0

使用Postgresql 9.5,希望知道索引表的最佳方式,以便以下查询不会使用顺序扫描。索引帮助(Postgresql不等于文本)

SELECT * 
FROM MYTABLE 
WHERE (
COL1 NOT IN ('980','982','983','984','985','986','987','988','989','990','991','996','997') 
OR 
COL2 <> '999' 
) 
+0

为什么你认为seq扫描不好?请[编辑]你的问题,并添加使用**'explain(analyze,verbose)'**生成的执行计划。 [_Formatted_](http://dba.stackexchange.com/help/formatting)**文本**请[无屏幕截图](http://meta.stackoverflow.com/questions/285551/why-may-i -not-upload-images-of-code-on-so-when-asking-question-285557#285557) –

+0

从来没有说过我认为他们是不好的 – Pyrite

+0

那么你为什么要避免它? –

回答

1

只要定义完全相同的部分索引,其中,在你的SELECT语句中使用子句:

CREATE INDEX ON mytable ((col1 IS NULL)) WHERE (
    COL1 NOT IN ('980','982','983','984','985','986','987','988','989','990','991','996','997') 
    OR 
    COL2 <> '999' 
) 

表达col1 IS NULL只是填充在其中产生存储一个布尔值在索引中,因为它是紧凑的(每行只有一个字节),并且不清楚列中哪些列是有意义的。如果您持续查询所有列,并且您不关心通过虚拟复制所有数据占用磁盘空间,那么在索引中包括所有列可能会使性能更有意义。

编辑:顺序扫描本身并不坏。通常,当PostgreSQL倾向于使用现有索引进行顺序扫描时,这有一个很好的理由。否则,可以调整配置以更准确地反映其服务器环境。