支持范围分区和列表分区
create table tbl_log(id int4,create_date date,log_type text);
create table tbl_log_sql(sql text) inherits(tbl_log);
\d tbl_log_sql
insert into tbl_log values(1,'2017-08-26',null);
insert into tbl_log_sql values(2,'2017-08-27',null,'select 2');
select * from tbl_log;
select tableoid,* from tbl_log;
select p.relname,c.* from tbl_log c, pg_class p where c.tableoid = p.oid;
--只显示父表数据
select * from only tbl_log;
delete from tbl_log;
select count(*) from tbl_log;
===
创建分区
create table log_ins(id serial,user_id int4,create_time timestamp(0) without timezone);
create table log_ins_history(check(create_time < '2017-01-01')) inherits(log_ins);
create table log_ins_history_201701(check(create_time >= '2017-01-01' and create_time < '2017-02-01')) inherits(log_ins);
create table log_ins_history_201702(check(create_time >= '2017-02-01' and create_time < '2017-03-01')) inherits(log_ins);
create table log_ins_history_201703(check(create_time >= '2017-03-01' and create_time < '2017-04-01')) inherits(log_ins);
create table log_ins_history_201704(check(create_time >= '2017-04-01' and create_time < '2017-05-01')) inherits(log_ins);
create table log_ins_history_201705(check(create_time >= '2017-05-01' and create_time < '2017-06-01')) inherits(log_ins);
create table log_ins_history_201706(check(create_time >= '2017-06-01' and create_time < '2017-07-01')) inherits(log_ins);
create table log_ins_history_201707(check(create_time >= '2017-07-01' and create_time < '2017-08-01')) inherits(log_ins);
create table log_ins_history_201708(check(create_time >= '2017-08-01' and create_time < '2017-09-01')) inherits(log_ins);
create table log_ins_history_201709(check(create_time >= '2017-09-01' and create_time < '2017-10-01')) inherits(log_ins);
create table log_ins_history_201710(check(create_time >= '2017-10-01' and create_time < '2017-11-01')) inherits(log_ins);
create table log_ins_history_201711(check(create_time >= '2017-11-01' and create_time < '2017-12-01')) inherits(log_ins);
create table log_ins_history_201712(check(create_time >= '2017-12-01' and create_time < '2018-01-01')) inherits(log_ins);
创建索引
create index idx_his_ctime on log_ins_history using btree(create_time);
create index idx_log_ins_201701_ctime on log_ins_history_201701 using btree(create_time);
create index idx_log_ins_201702_ctime on log_ins_history_201702 using btree(create_time);
create index idx_log_ins_201703_ctime on log_ins_history_201703 using btree(create_time);
create index idx_log_ins_201704_ctime on log_ins_history_201704 using btree(create_time);
create index idx_log_ins_201705_ctime on log_ins_history_201705 using btree(create_time);
create index idx_log_ins_201706_ctime on log_ins_history_201706 using btree(create_time);
create index idx_log_ins_201707_ctime on log_ins_history_201707 using btree(create_time);
create index idx_log_ins_201708_ctime on log_ins_history_201708 using btree(create_time);
create index idx_log_ins_201709_ctime on log_ins_history_201709 using btree(create_time);
create index idx_log_ins_201710_ctime on log_ins_history_201710 using btree(create_time);
create index idx_log_ins_201711_ctime on log_ins_history_201711 using btree(create_time);
create index idx_log_ins_201712_ctime on log_ins_history_201712 using btree(create_time);
创建函数
CREATE OR REPLACE FUNCTION log_ins_insert_trigger()
RETURNS trigger
LANGUAGE plpgsql
AS $function$
BEGIN
IF (NEW.create_time < '2017-01-01') THEN
INSERT INTO log_ins_history VALUES (NEW.*);
ELSIF( NEW.create_time >= '2017-01-01' and NEW.create_time < '2017-02-01') THEN
INSERT INTO log_ins_201701 VALUES (NEW.*);
ELSIF( NEW.create_time >= '2017-02-01' and NEW.create_time < '2017-03-01') THEN
INSERT INTO log_ins_201702 VALUES (NEW.*);
ELSIF( NEW.create_time >= '2017-03-01' and NEW.create_time < '2017-04-01') THEN
INSERT INTO log_ins_201703 VALUES (NEW.*);
ELSIF( NEW.create_time >= '2017-04-01' and NEW.create_time < '2017-05-01') THEN
INSERT INTO log_ins_201704 VALUES (NEW.*);
ELSIF( NEW.create_time >= '2017-05-01' and NEW.create_time < '2017-06-01') THEN
INSERT INTO log_ins_201705 VALUES (NEW.*);
ELSIF( NEW.create_time >= '2017-06-01' and NEW.create_time < '2017-07-01') THEN
INSERT INTO log_ins_201706 VALUES (NEW.*);
ELSIF( NEW.create_time >= '2017-07-01' and NEW.create_time < '2017-08-01') THEN
INSERT INTO log_ins_201707 VALUES (NEW.*);
ELSIF( NEW.create_time >= '2017-08-01' and NEW.create_time < '2017-09-01') THEN
INSERT INTO log_ins_201708 VALUES (NEW.*);
ELSIF( NEW.create_time >= '2017-09-01' and NEW.create_time < '2017-10-01') THEN
INSERT INTO log_ins_201709 VALUES (NEW.*);
ELSIF( NEW.create_time >= '2017-10-01' and NEW.create_time < '2017-11-01') THEN
INSERT INTO log_ins_201710 VALUES (NEW.*);
ELSIF( NEW.create_time >= '2017-11-01' and NEW.create_time < '2017-12-01') THEN
INSERT INTO log_ins_201711 VALUES (NEW.*);
ELSIF( NEW.create_time >= '2017-12-01' and NEW.create_time < '2018-01-01') THEN
INSERT INTO log_ins_201712 VALUES (NEW.*);
ELSE
RAISE EXCEPTION 'create_time out of range. Fix the log_ins_insert_trigger() function! ' ;
END IF;
RETURN NULL;
END;
$function$;
创建触发器
CREATE TRIGGER insert_log_ins_trigger BEFORE INSERT ON log_ins FOR EACH ROW
EXECUTE PROCEDURE log_ins_insert_trigger();
测试-插入数据
INSERT INTO log_ins (user_id, create_time)
SELECT round (100000000*random ()) ,generate_series ('2016-12-01'::date,'2017-12-01'::date, '1 minute');
select * from log_ins limit 2;
--查看父表,没数据
select count(*) from only log_ins;
--子表里面有数据
select count(*) from log_ins;
select min(create_time),max(create_time) from log_ins_201701;
\dt* log_ins*
性能测试
explain analyze select * from log_ins where create_time > '2017-01-01' and create_time < '2017-01-02';
explain analyze select * from log_ins_201701 where create_time > '2017-01-01' and create_time < '2017-01-02';
constraint_exclusing off on partition(*)
set constraint_exclusing = off;
explain analyze select * from log_ins where create_time > '2017-01-01' and create_time < '2017-01-02';
--添加分区
create table log_ins_201801(check(create_time >= '2018-01-01' and create time < '2018-02-01'))
create index idx_log_ins_201801_ctime on log_ins_201801 using btree(create_time);
CREATE OR REPLACE FUNCTION log_ins_insert_trigger()
RETURNS trigger
LANGUAGE plpgsql
AS $function$
BEGIN
IF (NEW.create_time < '2017-01-01') THEN
INSERT INTO log_ins_history VALUES (NEW.*);
ELSIF( NEW.create_time >= '2017-01-01' and NEW.create_time < '2017-02-01') THEN
INSERT INTO log_ins_201701 VALUES (NEW.*);
ELSIF( NEW.create_time >= '2017-02-01' and NEW.create_time < '2017-03-01') THEN
INSERT INTO log_ins_201702 VALUES (NEW.*);
ELSIF( NEW.create_time >= '2017-03-01' and NEW.create_time < '2017-04-01') THEN
INSERT INTO log_ins_201703 VALUES (NEW.*);
ELSIF( NEW.create_time >= '2017-04-01' and NEW.create_time < '2017-05-01') THEN
INSERT INTO log_ins_201704 VALUES (NEW.*);
ELSIF( NEW.create_time >= '2017-05-01' and NEW.create_time < '2017-06-01') THEN
INSERT INTO log_ins_201705 VALUES (NEW.*);
ELSIF( NEW.create_time >= '2017-06-01' and NEW.create_time < '2017-07-01') THEN
INSERT INTO log_ins_201706 VALUES (NEW.*);
ELSIF( NEW.create_time >= '2017-07-01' and NEW.create_time < '2017-08-01') THEN
INSERT INTO log_ins_201707 VALUES (NEW.*);
ELSIF( NEW.create_time >= '2017-08-01' and NEW.create_time < '2017-09-01') THEN
INSERT INTO log_ins_201708 VALUES (NEW.*);
ELSIF( NEW.create_time >= '2017-09-01' and NEW.create_time < '2017-10-01') THEN
INSERT INTO log_ins_201709 VALUES (NEW.*);
ELSIF( NEW.create_time >= '2017-10-01' and NEW.create_time < '2017-11-01') THEN
INSERT INTO log_ins_201710 VALUES (NEW.*);
ELSIF( NEW.create_time >= '2017-11-01' and NEW.create_time < '2017-12-01') THEN
INSERT INTO log_ins_201711 VALUES (NEW.*);
ELSIF( NEW.create_time >= '2017-12-01' and NEW.create_time < '2018-01-01') THEN
INSERT INTO log_ins_201712 VALUES (NEW.*);
ELSIF( NEW.create_time >= '2018-01-01' and NEW.create_time < '2018-02-01') THEN
INSERT INTO log_ins_201801 VALUES (NEW.*);
ELSE
RAISE EXCEPTION 'create_time out of range. Fix the log_ins_insert_trigger() function! ' ;
END IF;
RETURN NULL;
END;
$function$;
\d+ log_ins
方法二:
--创建分区
create table log_ins_201802(like log_ins including all);
--添加约束
alter table log_ins_201802 add constraint log_ins_201802_create_time_check check(create_time >= '2018-02-01' and create time < '2018-03-01');
--刷新触发器函数(刷新前先备份)
--继承
alter table log_ins_201802 inherit log_ins;
--删除分区
方法一:
drop table log_ins_201802
方法二:
alter table log_ins_201802 on inherit log_ins;
--分区表的查询
\d log_ins
\d+ log_ins
SQL 语句
--性能测试
create table log(id serial,user_id int4,create_time timestamp(0) without time zone);
INSERT INTO log (user_id, create_time)
SELECT round (100000000*random ()) ,generate_series ('2016-12-01'::date,'2017-12-01'::date, '1 minute');
select count(*) from log_ins;
select count(*) from log;
--创建索引
create index idx_log_userid on log using btree(user_id);
create index idx_log_create_time on log using btree(create_time);
create index idx_log_ins_userid on log_ins using btree(user_id);
create index idx_his_userid on log_ins_history using btree(user_id);
create index idx_log_ins_201701_userid on log_ins_201701 using btree(user_id);
create index idx_log_ins_201702_userid on log_ins_201702 using btree(user_id);
create index idx_log_ins_201703_userid on log_ins_201703 using btree(user_id);
create index idx_log_ins_201704_userid on log_ins_201704 using btree(user_id);
create index idx_log_ins_201705_userid on log_ins_201705 using btree(user_id);
create index idx_log_ins_201706_userid on log_ins_201706 using btree(user_id);
create index idx_log_ins_201707_userid on log_ins_201707 using btree(user_id);
create index idx_log_ins_201708_userid on log_ins_201708 using btree(user_id);
create index idx_log_ins_201709_userid on log_ins_201709 using btree(user_id);
create index idx_log_ins_201710_userid on log_ins_201710 using btree(user_id);
create index idx_log_ins_201711_userid on log_ins_201711 using btree(user_id);
create index idx_log_ins_201712_userid on log_ins_201712 using btree(user_id);
create index idx_log_ins_201801_userid on log_ins_201801 using btree(user_id);
网友评论