前些天拿到一個表,將近有4000w數據,沒有任何索引,主鍵。(建這表的絕對是我的才)mysql
這是一個日誌表,記錄了遊戲中物品的產出與消耗,原先有一個後臺對這個表進行統計。。。。。(這要用超級計算機才能統計得出來吧),只能幫前人填坑了。。。。sql
數據太大,決定用分區來重構。less
若是你發現是empty,說明你的mysql版本不夠,分區至少要5.1函數
下面針對業務查詢,決定用時間來作range分區(還有list,hash等類型),一個月一個區.優化
按照RANGE分區的表是經過以下一種方式進行分區的,每一個分區包含那些分區表達式的值位於一個給定的連續區間內的行。這些區間要連續且不能相互重疊,使用VALUES LESS THAN操做符來進行定義。ui
新建一個表:spa
CREATE TABLE xxxxxxxx
( crttm
int(11) NOT NULL, srvid
int(11) NOT NULL, evtid
int(11) NOT NULL, aid
int(11) NOT NULL, rid
int(11) NOT NULL, itmid
int(11) NOT NULL, itmnum
int(11) NOT NULL, gdtype
int(11) NOT NULL, gdnum
int(11) NOT NULL, islmt
int(11) NOT NULL,
KEY crttm
(crttm
),
KEY itemid
(itmid
),
KEY srvid
(srvid
),
KEY gdtype
(gdtype
)
) ENGINE=myisam DEFAULT CHARSET=utf8
PARTITION BY RANGE (crttm)
(
PARTITION p201303 VALUES LESS THAN (unix_timestamp('2013-04-01')),
PARTITION p201304 VALUES LESS THAN (unix_timestamp('2013-05-01')),
PARTITION p201305 VALUES LESS THAN (unix_timestamp('2013-06-01')),
PARTITION p201306 VALUES LESS THAN (unix_timestamp('2013-07-01')),
PARTITION p201307 VALUES LESS THAN (unix_timestamp('2013-08-01')),
PARTITION p201308 VALUES LESS THAN (unix_timestamp('2013-09-01')),
PARTITION p201309 VALUES LESS THAN (unix_timestamp('2013-10-01')),
PARTITION p201310 VALUES LESS THAN (unix_timestamp('2013-11-01')),
PARTITION p201311 VALUES LESS THAN (unix_timestamp('2013-12-01')),
PARTITION p201312 VALUES LESS THAN (unix_timestamp('2014-01-01')),
PARTITION p201401 VALUES LESS THAN (unix_timestamp('2014-02-01'))
);unix
注意:日誌
mysql> create unique index idx_employees1_job_code on employees1(job_code);
ERROR 1503 (HY000): A UNIQUE INDEX must include all columns in the table's partitioning function
或
mysql> ALTER TABLE skate
.employees1
ADD PRIMARY KEY (id
) ;
ERROR 1503 (HY000): A PRIMARY KEY must include all columns in the table's partitioning functioncode
將舊的表數據導入到新表後,看到新表的數據都分佈到不一樣的區了!
維護命令:
添加分區
alter table xxxxxxx add partition (partition p0 values less than(1991)); //只能添加大於分區鍵的分區
刪除分區
alter table xxxxxxx drop partition p0; //能夠刪除任意分區
刪除分區數據
alter table xxxxxx truncate partition p1,p2;
alter table xxxxxx truncate partition all;
或
delete from xxxxxx where separated < '2006-01-01' or (separated >= '2006-01-01' and separated<'2011-01-01');
重定義分區(包括重命名分區,伴隨移動數據;合併分區)
alter table xxxxx reorganize partition p1,p3,p4 into (partition pm1 values less than(2006),
partition pm2 values less than(2011));
rebuild重建分區
alter table xxxxxx rebuild partition pm1/all; //至關於drop全部記錄,而後再reinsert;能夠解決磁盤碎片
優化表
alter table tt2 optimize partition pm1; //在大量delete表數據後,能夠回收空間和碎片整理。但在5.5.30後支持。在5.5.30以前能夠經過recreate+analyze來替代,若是用rebuild+analyze速度慢
analzye表
alter table xxxxxx analyze partition pm1/all;
check表
alter table xxxxxx check partition pm1/all;
show create table employees2; //查看分區表的定義
show table status like 'employees2'G; //查看錶時候是分區表 如「Create_options: partitioned」
select * from information_schema.KEY_COLUMN_USAGE where table_name='employees2'; //查看索引
SELECT * FROM information_schema.partitions WHERE table_name='employees2' //查看分區表
explain partitions select * from employees2 where separated < '1990-01-01' or separated > '2016-01-01'; //查看分區是否被select使用
zhuzy