欢迎来到「数据库装修大队」!今天我们将化身"数据空间规划师",用一家年订单量破亿的外卖平台崩溃案例,教你如何像整理衣柜一样优雅管理海量数据。
血泪案例:
某外卖平台未做分区,导致:
分区表的三板斧:
行业黑话:分区键就像快递分拣码——
order_time
是时间分拣码,city_id
是地区分拣码
-- 按订单时间分舱(每月一个分区)
CREATE TABLE orders (
id BIGINT,
order_time DATETIME,
amount DECIMAL(10,2)
) PARTITION BY RANGE (YEAR(order_time)*100 + MONTH(order_time)) (
PARTITION p202301 VALUES LESS THAN (202302),
PARTITION p202302 VALUES LESS THAN (202303),
PARTITION p202312 VALUES LESS THAN (202401)
);
适用场景:时序数据(订单、日志)——就像把日记按月分册
-- 按城市分舱(北方/南方)
CREATE TABLE sales (
id INT,
city VARCHAR(20),
sales_amount DECIMAL
) PARTITION BY LIST (city) (
PARTITION p_north VALUES IN ('北京','天津','沈阳'),
PARTITION p_south VALUES IN ('广州','深圳','海口')
);
搞笑场景:当新增"重庆市"时——DBA需要像地图编辑一样手动添加新区划
-- 按用户ID哈希分舱
CREATE TABLE user_logs (
user_id BIGINT,
log_time DATETIME,
action VARCHAR(20)
) PARTITION BY HASH(user_id)
PARTITIONS 8;
玄学特性:数据随机分布,专治"热点数据"——就像把VIP客户随机分到不同柜台
外卖平台救星代码:
-- 创建时间范围分区表
CREATE TABLE orders (
order_id BIGINT,
user_id INT,
order_time DATETIME,
restaurant_id INT,
amount DECIMAL(10,2)
)
PARTITION BY RANGE (TO_DAYS(order_time)) (
PARTITION p2023q1 VALUES LESS THAN (TO_DAYS('2023-04-01')),
PARTITION p2023q2 VALUES LESS THAN (TO_DAYS('2023-07-01')),
PARTITION p2023q3 VALUES LESS THAN (TO_DAYS('2023-10-01')),
PARTITION p2023q4 VALUES LESS THAN (TO_DAYS('2024-01-01'))
);
-- 查看分区结构
SELECT partition_name, table_rows
FROM information_schema.partitions
WHERE table_name = 'orders';
输出效果:
+----------------+------------+
| partition_name | table_rows |
+----------------+------------+
| p2023q1 | 12,345,678 |
| p2023q2 | 15,789,456 | ← 每个分区独立计数
+----------------+------------+
技巧1:分区裁剪(Partition Pruning)
-- 查询Q2季度的订单
EXPLAIN
SELECT * FROM orders
WHERE order_time BETWEEN '2023-04-01' AND '2023-06-30';
执行计划惊喜:
| id | select_type | partitions | ...
| 1 | SIMPLE | p2023q2 | ← 只扫描目标分区!
技巧2:并行查询加速
-- 跨分区聚合统计
SELECT YEAR(order_time), SUM(amount)
FROM orders
PARTITION (p2023q1, p2023q2)
GROUP BY YEAR(order_time);
就像同时派多个快递员去不同仓库取件
全局索引 vs 本地索引:
-- 全局索引(跨分区大锁)
CREATE INDEX idx_user ON orders(user_id);
-- 本地索引(分区独立小锁)
CREATE INDEX idx_restaurant ON orders(restaurant_id) LOCAL;
性能对决:
日常操作三件套:
-- 添加新分区(迎接下季度数据)
ALTER TABLE orders ADD PARTITION (
PARTITION p2024q1 VALUES LESS THAN (TO_DAYS('2024-04-01'))
);
-- 合并历史分区(归档旧数据)
ALTER TABLE orders COALESCE PARTITION 4;
-- 重建问题分区(修复数据损坏)
ALTER TABLE orders REBUILD PARTITION p2023q2;
紧急情况处理:
-- 快速删除旧数据(直接删分区)
ALTER TABLE orders DROP PARTITION p2020q1; -- 比DELETE快100倍!
-- 分区数据迁移(物理文件搬运)
ALTER TABLE orders EXCHANGE PARTITION p2023q1
WITH TABLE orders_archive;
现在你已经成为"分区表领域的空间魔法师"!下一章我们将进入《触发器与存储过程——数据库的"自动机器人"和"万能工具箱"》的科幻世界,记得给你的服务器准备液氮冷却——数据洪流要来了! ❄️