postgresql索引类型介绍以及管理

引言

在数据库日常巡检过程中,经常会有一些表上线后遇到更新导致弃用而未能及时下线,此时索引就会占用一定的存储空间。定期的数据库巡检,删除掉无用的索引,为数据库释放空间就变得含有必要,根据业务量级可以定期一个月、一个季度进行索引探查。

索引分类

在psql客户端可以通过源命令查看索引种类

postgres=# \dA+
                             List of access methods
  Name  | Type  |       Handler        |              Description               
--------+-------+----------------------+----------------------------------------
 brin   | Index | brinhandler          | block range index (BRIN) access method
 btree  | Index | bthandler            | b-tree index access method
 gin    | Index | ginhandler           | GIN index access method
 gist   | Index | gisthandler          | GiST index access method
 hash   | Index | hashhandler          | hash index access method
 heap   | Table | heap_tableam_handler | heap table access method
 spgist | Index | spghandler           | SP-GiST index access method
(7 rows)


postgres=# SELECT amname AS "Name",
postgres-#   CASE amtype WHEN 'i' THEN 'Index' WHEN 't' THEN 'Table' END AS "Type",
postgres-#   amhandler AS "Handler",
postgres-#   pg_catalog.obj_description(oid, 'pg_am') AS "Description"
postgres-# FROM pg_catalog.pg_am
postgres-# ;
  Name  | Type  |       Handler        |              Description               
--------+-------+----------------------+----------------------------------------
 heap   | Table | heap_tableam_handler | heap table access method
 btree  | Index | bthandler            | b-tree index access method
 hash   | Index | hashhandler          | hash index access method
 gist   | Index | gisthandler          | GiST index access method
 gin    | Index | ginhandler           | GIN index access method
 spgist | Index | spghandler           | SP-GiST index access method
 brin   | Index | brinhandler          | block range index (BRIN) access method
(7 rows)

其中  Type=Index的为目前数据库支持的索引  heap

BTREE

btree:操作符类必须提供五种比较操作符:<、<=、=、>=以及>。<>不会在索引搜索中使用有<>的WHERE子句(规划器会认为<>与一个btree操作符类相关,但它是通过=操作符的逆操作符链接来找到这个操作符,而不是从pg_amop中查找)。最常用的索引,BTree索引适合用于处理等值查询和范围查询。

<、<=、=、>=、>

HASH

hash:Hash索引只能处理简单等值比较

=

GIST

gist:常用在二维平面上的操作索引,PostgreSQL的标准发布中包含了用于二维几何数据类型的GiST操作符类。官方对于这个索引的解释:GiST索引并不是一种单独的索引,而是可以用于实现很多不同索引策略的基础设施。相应地,可以使用一个GiST索引的特定操作符根据索引策略(操作符类)而变化

例如GiST索引也有能力优化“最近邻”搜索

<<   &<   &>   >>   <<|   &<|   |&>   |>>   @>   <@   ~=   &&
SELECT * FROM places ORDER BY location <-> point '(101,456)' LIMIT 10;

GIN

GIN 索引是“倒排索引”,它适合于包含多个组成值的数据值,常用于数组相关类型的操作符

<@   @>   =   &&

SPGIST

SP-GiST是“Space-Partitioned GiST”的缩写,即空间分区GiST索引。常用空间操作符运算的索引
<<   >>   ~=   <@   <<|   |>>

BRIN

BRIN 索引(块范围索引的缩写)存储有关存放在一个表的连续物理块范围上的值摘要信息

<   <=   =   >=   >

创建语法

CREATE [ UNIQUE ] INDEX [ CONCURRENTLY ] [ [ IF NOT EXISTS ] name ] ON [ ONLY ] table_name [ USING method ]
    ( { column_name | ( expression ) } [ COLLATE collation ] [ opclass [ ( opclass_parameter = value [, ... ] ) ] ] [ ASC | DESC ] [ NULLS { FIRST | LAST } ] [, ...] )
    [ INCLUDE ( column_name [, ...] ) ]
    [ NULLS [ NOT ] DISTINCT ]
    [ WITH ( storage_parameter [= value] [, ... ] ) ]
    [ TABLESPACE tablespace_name ]
    [ WHERE predicate ]

重点参数介绍


method
要使用的索引方法的名称。可以选择 btree、hash、 gist、spgist、 gin以及brin。 默认方法是btree。

column_name
一个表列的名称。

expression
一个基于一个或者更多个表列的表达式。如语法中所示,表达式通常必须 被写在圆括号中。不过,如果该表达式是一个函数调用的形式,圆括号可 以被省略。

collation
要用于该索引的排序规则的名称。默认情况下,该索引使用被索引列 的排序规则或者被索引表达式的结果排序规则。当查询涉及到使用非 默认排序规则的表达式时,使用非默认排序规则的索引就能排上用场。

opclass
一个操作符类的名称。详见下文。

ASC
指定上升排序(默认)。

DESC
指定下降排序。

NULLS FIRST
指定把空值排序在非空值前面。在指定DESC时, 这是默认行为。

NULLS LAST
指定把空值排序在非空值后面。在没有指定DESC时, 这是默认行为。

storage_parameter
索引方法相关的存储参数的名称。详见 索引存储参数。

tablespace_name
在其中创建索引的表空间。如果没有指定,将会使用 default_tablespace。或者对临时表上的索引使用 temp_tablespaces。

predicate
部分索引的约束表达式

索引对空间的影响

create  table index_text(id int,text varchar(200));
insert into index_text(id , text)   select generate_series(1928,97356), md5(generate_series(1928,97356)::text);


--未加索引时的表大小
SELECT pg_size_pretty(pg_total_relation_size('index_text')) ;


--未加过滤字段索引 检索走全表扫描
explain analyze select  *  from  index_text where id=4 ;


--增加索引
create index index_text_id on index_text(id);

--加索引时的表大小
SELECT pg_size_pretty(pg_total_relation_size('index_text')) ;


--增加索引后通过索引字段,表扫描索引扫描
explain analyze select  *  from  index_text where id= 4 ;

增加索引后会增加表的空间大小  

postgres=# SELECT pg_size_pretty(pg_total_relation_size('index_text')) ;
 pg_size_pretty 
----------------
 6392 kB
(1 row)


postgres=# create index index_text_id on index_text(id);
CREATE INDEX
postgres=# SELECT pg_size_pretty(pg_total_relation_size('index_text')) ;
 pg_size_pretty 
----------------
 8504 kB
(1 row)

查看表中索引信息

SELECT n.nspname as "Schema",
  c.relname as "Name",
  CASE c.relkind WHEN 'r' THEN 'table' WHEN 'v' THEN 'view' WHEN 'm' THEN 'materialized view' WHEN 'i' THEN 'index' WHEN 'S' THEN 'sequence' WHEN 't' THEN 'TOAST table' WHEN 'f' THEN 'foreign table' WHEN 'p' THEN 'partitioned table' WHEN 'I' THEN 'partitioned index' END as "Type",
  pg_catalog.pg_get_userbyid(c.relowner) as "Owner",
  c2.relname as "Table",
  CASE c.relpersistence WHEN 'p' THEN 'permanent' WHEN 't' THEN 'temporary' WHEN 'u' THEN 'unlogged' END as "Persistence",
  am.amname as "Access method",
  pg_catalog.pg_size_pretty(pg_catalog.pg_table_size(c.oid)) as "Size",
  pg_catalog.obj_description(c.oid, 'pg_class') as "Description"
FROM pg_catalog.pg_class c
     LEFT JOIN pg_catalog.pg_namespace n ON n.oid = c.relnamespace
     LEFT JOIN pg_catalog.pg_am am ON am.oid = c.relam
     LEFT JOIN pg_catalog.pg_index i ON i.indexrelid = c.oid
     LEFT JOIN pg_catalog.pg_class c2 ON i.indrelid = c2.oid
WHERE c.relkind IN ('i','I','')
      AND n.nspname <> 'pg_catalog'
      AND n.nspname !~ '^pg_toast'
      AND n.nspname <> 'information_schema'
  AND pg_catalog.pg_table_is_visible(c.oid)
ORDER BY 1,2; 

                              List of relations
 Schema |         Name          | Type  |  Owner   |      Table       | Persistence | Access method |  Size   | Description 
--------+-----------------------+-------+----------+------------------+-------------+---------------+---------+-------------
 public | index_text_id         | index | postgres | index_text       | permanent   | btree         | 2104 kB | 
 public | pgbench_branches_pkey | index | postgres | pgbench_branches | permanent   | btree         | 16 kB   | 
 public | pgbench_tellers_pkey  | index | postgres | pgbench_tellers  | permanent   | btree         | 16 kB   | 

或者使用元命令

\di
\di+

查看索引调用情况

select * from  pg_stat_all_indexs;

--检索是尽量加上schemaname的约束条件,排除掉系统的pg_catalog, pg_toast


--或者使用
select  * from  pg_stat_user_indexes     --排除掉系统schemaname 查看    

- relid:索引所属的表的对象标识符(OID)。
- indexrelid:索引的对象标识符(OID)。
- schemaname:索引所属的模式名称。
- relname:索引所属的表名称。
- indexrelname:索引名称。
- idx_scan:自上次统计以来,索引被扫描的次数。
- idx_tup_read:自上次统计以来,从索引中读取的行数。
- idx_tup_fetch:自上次统计以来,从索引中获取的行数。

定期做增量计数  ,重点观察使用频率低的索引。

你可能感兴趣的:(dba,数据库,postgresql,大数据,oracle,sql,database)