mysql改名表,并创建一张原来一模一样的表备份表
一、MySQL 重命名表
语法
-- 方式1(通用)
ALTER TABLE 旧表名 RENAME TO 新表名;
-- 方式2(跨库也可用,推荐)
RENAME TABLE 旧表名 TO 新表名;示例
原表 user,改名为 user_old:
ALTER TABLE `user` RENAME TO `user_old`;二、复制原表结构(空表,仅结构、索引、字段,不复制数据)
-- 语法
CREATE TABLE 新表名 LIKE 源表名;
-- 示例:创建和 user_old 结构完全一致的新表 user
CREATE TABLE `user` LIKE `user_old`;三、如果需要连数据一起复制(结构+数据全量克隆)
-- 结构 + 数据 一起复制
CREATE TABLE 新表名 SELECT * FROM 源表名;完整流程示例(常用场景:旧表改名 + 新建同结构空表)
-- 1. 把原有业务表改名备份
ALTER TABLE `test_table` RENAME TO `test_table_bak`;
-- 2. 创建一张和原表结构完全相同的新空表
CREATE TABLE `test_table` LIKE `test_table_bak`;补充说明
LIKE方式会完整复制字段、数据类型、主键、索引、默认值、注释,不会复制数据;- 执行前建议先锁表/停业务,避免数据写入导致不一致;
- 表名建议用反引号
`包裹,防止和关键字冲突。
关于 ALTER TABLE 和 RENAME TABLE 这两种语法的区别,速度和原理是否一样:
-- 方式1(通用)
ALTER TABLE 旧表名 RENAME TO 新表名;
-- 方式2(跨库也可用,推荐)两种表改名语法:区别、原理、速度
一、核心结论
底层原理、执行速度基本一致,都是元数据级操作(瞬间完成,不改动表数据),主要差异在语法能力、使用场景、语法规范。
二、详细区别
1. 语法与标准归属
ALTER TABLE 旧名 RENAME TO 新名- 属于
ALTER TABLE子语法,是 SQL 标准衍生写法。 - 仅支持单表改名,不能跨数据库。
- 语法语义:修改表的名称属性。
- 属于
RENAME TABLE 旧名 TO 新名- MySQL 专属扩展语法,功能更强。
- 支持单表 / 多表批量改名、跨数据库迁移表。
多表示例:
RENAME TABLE t1 TO t1_bak, t2 TO t2_bak;跨库示例(把
db1.tbl移到db2并重命名):RENAME TABLE db1.tbl TO db2.tbl_new;
2. 权限要求
- 两者都需要原表的
ALTER权限。 - 跨库使用
RENAME TABLE时,需要目标库的 CREATE 权限。
3. 锁机制 & 并发(InnoDB)
两者在 InnoDB 下行为一致:
- 均为元数据操作,仅修改数据字典、文件映射,不拷贝行数据。
- 执行时会加 MDL 元数据锁,短时间阻塞 DDL/DML,锁持有时间极短。
- 不存在 IO 读写,速度完全相同,都是毫秒级。
4. 兼容性
ALTER TABLE ... RENAME:兼容更多数据库(MariaDB、部分其他SQL库),通用性更好。RENAME TABLE:纯 MySQL 专用,其他数据库不识别。
三、原理(完全一致)
MySQL 表名本质只是数据字典里的标识,同时对应磁盘上 .frm、.ibd 等文件名称:
- 两种语法都不遍历、不迁移表内数据;
- 仅修改:数据字典记录 + 磁盘上表相关文件名称;
- InnoDB 共享表空间/独立表空间,行为无区别。
四、使用场景建议
- 同库、单表、追求通用兼容 → 用
ALTER TABLE ... RENAME TO - 跨库、批量改表名、MySQL 专属环境 → 优先
RENAME TABLE - 速度不用纠结:二者性能无差异。
RENAME TABLE 旧表名 TO 新表名;
实战:备份日志表并创建新的日志表,用到变量、动态SQL执行
-- 定义变量:拼接 表名_年月日
SET @old_tb = 'sp_log';
SET @suffix = DATE_FORMAT(CURDATE(), '%Y%m%d');
SET @bak_tb = CONCAT(@old_tb, '_', @suffix);
-- 2. 第一条:重命名旧表
SET @sql1 = CONCAT('RENAME TABLE `', @old_tb, '` TO `', @bak_tb, '`;');
PREPARE stmt1 FROM @sql1;
EXECUTE stmt1;
DEALLOCATE PREPARE stmt1;
-- 3. 第二条:新建同结构空表
SET @sql2 = CONCAT('CREATE TABLE `', @old_tb, '` LIKE `', @bak_tb, '`;');
PREPARE stmt2 FROM @sql2;
EXECUTE stmt2;
DEALLOCATE PREPARE stmt2;如果你尝试将两条SQL放到一个预定义语句中执行,将喜提一个报错:
报错原因
MySQL 一条预处理语句里不能同时放两条独立 SQL(RENAME + CREATE 写在同一个字符串里),解析时直接语法报错。
预处理 PREPARE 单次只支持单条 SQL 语句。
SET @sql = CONCAT(
'RENAME TABLE `', @old_tb, '` TO `', @bak_tb, '`;',
'CREATE TABLE `', @old_tb, '` LIKE `', @bak_tb, '`;'
);
PREPARE stmt FROM @sql;
EXECUTE stmt;
DEALLOCATE PREPARE stmt;版权属于:Joyber
本文链接:https://blog.qqvbc.com/default/1479.html
转载时须注明出处及本声明