mysql分区表语法
1.创建分区表
分区键需要和主键设置为复合主键,分区表不可直接转换成非分区表,需要重新建非分区表并导入数据
- 按年份
create table partitioned_table_year (
id int,
content varchar(50),
created_time datetime,
primary key (id,created_time)
) partition by range(year(created_time)) (
partition p2024 values less than (2025),
partition p2025 values less than (2026),
partition p2026 values less than (2027)
);- 按月份
create table partitioned_table_month (
id int,
content varchar(50),
created_time datetime,
primary key (id,created_time)
) partition by range columns(created_time) (
partition p202410 values less than ('2024-11-01'),
partition p202411 values less than ('2024-12-01'),
partition p202412 values less than ('2025-01-01')
);- 修改表结构,增加分区
alter table `partitioned_table_month` modify column `created_time` datetime(0) not null ,
drop primary key,
add primary key (`id`, `created_time`) using btree;
alter table partitioned_table_month partition by range columns(created_time) (
partition p202410 values less than ('2024-11-01'),
partition p202411 values less than ('2024-12-01'),
partition p202412 values less than ('2025-01-01')
);- 删除分区,注意:删除分区的时候会同时删除数据
alter table partitioned_table_month drop partition p202407,p202408;
2.查询
- 查看表分区
select
table_name,
partition_name,
partition_method,
partition_expression,
partition_description,
table_rows,
avg_row_length,
data_length,
index_length
from
information_schema.partitions
where
table_schema = 'xxx' and table_name = 'partitioned_table_month'; - 查看分区数据
select * from partitioned_table partition (p2024,p2025)
3.利用存储过程批量修改非分区表为分区表
- 创建联合主键存储过程,先设置联合主键字段非空,再删除原id去掉主键,再设置联合主键
delimiter $$
drop procedure if exists auto_create_pk$$
create procedure `auto_create_pk`(in `table_name` varchar(64),in `column_name` varchar(64),in `column_comment` varchar(64))
begin
set @sql = concat("alter table `",table_name,"` modify column `",column_name,"` datetime not null comment '",column_comment,"',
drop primary key,
add primary key ( `id`, `",column_name,"` ) using btree;");
prepare stmt from @sql;
execute stmt;
deallocate prepare stmt;
end$$
delimiter ;- 创建按年自动分区存储过程
delimiter $$
drop procedure if exists auto_create_partition_year$$
create procedure `auto_create_partition_year`(in `table_name` varchar(64),in `column_name` varchar(64))
begin
declare partitioned longtext;
declare n int;
set n = 2025;
set partitioned = '';
while n <= 2027 do
set partitioned = concat(partitioned,",partition p",n," values less than (",n+1,")");
set n = n + 1;
end while;
set @sql = concat ("alter table ",table_name," partition by range(year(",column_name,")) (",substr(partitioned,2,length(partitioned)),");") ;
prepare stmt from @sql;
execute stmt;
deallocate prepare stmt;
end$$
delimiter ;- 创建按月自动分区存储过程
delimiter $$
drop procedure if exists auto_create_partition_month$$
create procedure `auto_create_partition_month`(in `table_name` varchar(64),in `column_name` varchar(64))
begin
declare partitioned longtext;
declare n int;
declare m int;
set n = 2015;
set partitioned = '';
while n <= 2030 do
set m = 1;
while m < 12 do
set partitioned = concat(partitioned,",partition p",n,lpad(m,2,0)," values less than ('",n,"-",lpad(m+1,2,0),"-01')");
set m = m + 1;
end while;
if m = 12 then
set partitioned = concat(partitioned,",partition p",n,"12 values less than ('",n+1,"-01-01')");
end if;
set n = n + 1;
end while;
set @sql = concat ("alter table ",table_name," partition by range columns(",column_name,") (",substr(partitioned,2,length(partitioned)),");") ;
prepare stmt from @sql;
execute stmt;
deallocate prepare stmt;
end$$
delimiter ;-- 查询存储过程
show procedure status like 'auto_create_partition%';
-- 执行联合主键
call auto_create_pk('table_a','a_time','时间');
-- 执行按年自动分区
call auto_create_partition_year('table_b','b_time');
-- 执行按月自动分区
call auto_create_partition_month('table_c','c_time'); 总结
以上为个人经验,希望能给大家一个参考,也希望大家多多支持代码网。
发表评论