PostgreSQL UUID 类型性能
PostgreSQL UUID type performance
我不是要重启 UUID 与串行整数密钥的争论。我知道任何一方都有有效的观点。我在我的几个表中使用 UUID 作为主键。
- 列类型:
"uuidKey" text NOT NULL
- 索引:
CREATE UNIQUE INDEX grand_pkey ON grand USING btree ("uuidKey")
- 主键约束:
ADD CONSTRAINT grand_pkey PRIMARY KEY ("uuidKey");
这是我的第一个问题;对于 PostgreSQL 9.4,将列类型设置为 UUID 是否有任何性能优势?
文档 http://www.postgresql.org/docs/9.4/static/datatype-uuid.html 描述了 UUID,但是使用此类型而不是 text
类型除了类型安全之外还有什么好处吗?在字符类型文档中,它表明 char(n)
与 PostgreSQL 中的 text
相比没有任何优势。
Tip: There is no performance difference among these three types, apart
from increased storage space when using the blank-padded type, and a
few extra CPU cycles to check the length when storing into a
length-constrained column. While character(n) has performance
advantages in some other database systems, there is no such advantage
in PostgreSQL; in fact character(n) is usually the slowest of the
three because of its additional storage costs. In most situations text
or character varying should be used instead.
我不担心磁盘 space,我只是想知道我是否值得花时间对 UUID 与文本列类型进行基准测试?
第二个问题,hash vs b-tree 索引。对 UUID 键进行排序没有任何意义,那么 b-tree 是否比哈希索引有任何其他优势?
A UUID
是一个 16 字节的值。与 text
相同的是一个 32 字节的值。存储大小为:
select
pg_column_size('a0eebc999c0b4ef8bb6d6bb9bd380a11'::text) as text_size,
pg_column_size('a0eebc999c0b4ef8bb6d6bb9bd380a11'::uuid) as uuid_size;
text_size | uuid_size
-----------+-----------
36 | 16
表越小,操作越快。
我们有一个 table 大约 30k 行(出于特定的不相关架构原因)将 UUID 存储在文本字段中并建立索引。我注意到查询性能比我预期的要慢。我创建了一个新的 UUID 列,复制到文本 uuid 主键中并在下面进行比较。 2.652 毫秒对 0.029 毫秒。完全不同!
-- With text index
QUERY PLAN
Index Scan using tmptable_pkey on tmptable (cost=0.41..1024.34 rows=1 width=1797) (actual time=0.183..2.632 rows=1 loops=1)
Index Cond: (primarykey = '755ad490-9a34-4c9f-8027-45fa37632b04'::text)
Planning time: 0.121 ms
Execution time: 2.652 ms
-- With a uuid index
QUERY PLAN
Index Scan using idx_tmptable on tmptable (cost=0.29..2.51 rows=1 width=1797) (actual time=0.012..0.013 rows=1 loops=1)
Index Cond: (uuidkey = '755ad490-9a34-4c9f-8027-45fa37632b04'::uuid)
Planning time: 0.109 ms
Execution time: 0.029 ms
我不是要重启 UUID 与串行整数密钥的争论。我知道任何一方都有有效的观点。我在我的几个表中使用 UUID 作为主键。
- 列类型:
"uuidKey" text NOT NULL
- 索引:
CREATE UNIQUE INDEX grand_pkey ON grand USING btree ("uuidKey")
- 主键约束:
ADD CONSTRAINT grand_pkey PRIMARY KEY ("uuidKey");
这是我的第一个问题;对于 PostgreSQL 9.4,将列类型设置为 UUID 是否有任何性能优势?
文档 http://www.postgresql.org/docs/9.4/static/datatype-uuid.html 描述了 UUID,但是使用此类型而不是 text
类型除了类型安全之外还有什么好处吗?在字符类型文档中,它表明 char(n)
与 PostgreSQL 中的 text
相比没有任何优势。
Tip: There is no performance difference among these three types, apart from increased storage space when using the blank-padded type, and a few extra CPU cycles to check the length when storing into a length-constrained column. While character(n) has performance advantages in some other database systems, there is no such advantage in PostgreSQL; in fact character(n) is usually the slowest of the three because of its additional storage costs. In most situations text or character varying should be used instead.
我不担心磁盘 space,我只是想知道我是否值得花时间对 UUID 与文本列类型进行基准测试?
第二个问题,hash vs b-tree 索引。对 UUID 键进行排序没有任何意义,那么 b-tree 是否比哈希索引有任何其他优势?
A UUID
是一个 16 字节的值。与 text
相同的是一个 32 字节的值。存储大小为:
select
pg_column_size('a0eebc999c0b4ef8bb6d6bb9bd380a11'::text) as text_size,
pg_column_size('a0eebc999c0b4ef8bb6d6bb9bd380a11'::uuid) as uuid_size;
text_size | uuid_size
-----------+-----------
36 | 16
表越小,操作越快。
我们有一个 table 大约 30k 行(出于特定的不相关架构原因)将 UUID 存储在文本字段中并建立索引。我注意到查询性能比我预期的要慢。我创建了一个新的 UUID 列,复制到文本 uuid 主键中并在下面进行比较。 2.652 毫秒对 0.029 毫秒。完全不同!
-- With text index
QUERY PLAN
Index Scan using tmptable_pkey on tmptable (cost=0.41..1024.34 rows=1 width=1797) (actual time=0.183..2.632 rows=1 loops=1)
Index Cond: (primarykey = '755ad490-9a34-4c9f-8027-45fa37632b04'::text)
Planning time: 0.121 ms
Execution time: 2.652 ms
-- With a uuid index
QUERY PLAN
Index Scan using idx_tmptable on tmptable (cost=0.29..2.51 rows=1 width=1797) (actual time=0.012..0.013 rows=1 loops=1)
Index Cond: (uuidkey = '755ad490-9a34-4c9f-8027-45fa37632b04'::uuid)
Planning time: 0.109 ms
Execution time: 0.029 ms