PostgreSQL does not use proper partition on UPDATE statement

限于喜欢 提交于 2019-12-10 12:21:17

问题


Executing a regular UPDATE statement on a partitioned table seems to be worst than doing it in a regular one.

Setup

CREATE TABLE users
(
  id   VARCHAR(10) NOT NULL,
  name VARCHAR(10) NOT NULL
) PARTITION BY HASH (id);

ALTER TABLE users ADD PRIMARY KEY (id);

CREATE TABLE users_p0 PARTITION OF users FOR VALUES WITH (MODULUS 3, REMAINDER 0);
CREATE TABLE users_p1 PARTITION OF users FOR VALUES WITH (MODULUS 3, REMAINDER 1);
CREATE TABLE users_p2 PARTITION OF users FOR VALUES WITH (MODULUS 3, REMAINDER 2);

INSERT INTO users (id, name) VALUES ('1', 'Blue');
INSERT INTO users (id, name) VALUES ('2', 'Green');
INSERT INTO users (id, name) VALUES ('3', 'Red');
INSERT INTO users (id, name) VALUES ('4', 'Yellow');

Query plan for SELECT statement

EXPLAIN SELECT * FROM users WHERE id = '1';

Result (cost=0.15..2.37)

Append  (cost=0.15..2.37 rows=1 width=76)
  ->  Index Scan using users_p0_pkey on users_p0  (cost=0.15..2.37 rows=1 width=76)
        Index Cond: ((id)::text = '1'::text)

Query plan for UPDATE statement

EXPLAIN UPDATE users SET name = 'New blue' WHERE id = '1';

Result (cost=0.15..7.10)

Update on users  (cost=0.15..7.10 rows=3 width=82)
  Update on users_p0
  Update on users_p1
  Update on users_p2
  ->  Index Scan using users_p0_pkey on users_p0  (cost=0.15..2.37 rows=1 width=82)
        Index Cond: ((id)::text = '1'::text)
  ->  Index Scan using users_p1_pkey on users_p1  (cost=0.15..2.37 rows=1 width=82)
        Index Cond: ((id)::text = '1'::text)
  ->  Index Scan using users_p2_pkey on users_p2  (cost=0.15..2.37 rows=1 width=82)
        Index Cond: ((id)::text = '1'::text)

I expected the query planner to access directly to users_p0 instead of accessing all partitions

来源:https://stackoverflow.com/questions/54483353/postgresql-does-not-use-proper-partition-on-update-statement

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!