Mysql更新百万历史数据
场景
目前在main库里有一张main_test表,数据大约1000万
CREATE TABLEmain.main_test(id BIGINT NOT NULL COMMENT '主键ID',name VARCHAR(100) COMMENT '名称',PRIMARY KEY (id))ENGINE=InnoDB DEFAULT CHARSET=utf8 COMMENT='主表';
需求为给main_test表添加一code列
ALTER TABLE main_test ADD COLUMN code VARCHAR(60) COMMENT '代码' AFTER id ;
然后从另一个数据库sla的表slave_test关联更新main_test表的code,具体关联关系为
UPDATE main.main_test mt INNER JOIN sla.slave_test st ON mt.name = st.name SET mt.code = st.code;
问题
- main_test表与slave_test表不在同一个库,因此不能直接关联更新
- 即使在同一个库,但是main_test表数据量大,并且name字段没有索引,也不能临时添加索引,强行在生产环境更新会因为锁表阻塞导致应用雪崩
解决方案
1、在main库创建临时表main_test_tmp
CREATE TABLEmain.main_test_tmp(id INT AUTO_INCREMENT PRIMARY KEY NOT NULL COMMENT '主键ID',test_id BIGINT COMMENT 'main_test表主键', name VARCHAR(100) COMMENT '名称',code VARCHAR(60) COMMENT '代码')ENGINE=InnoDB DEFAULT CHARSET=utf8 COMMENT='主表';
2、查询slave_test表并导出到文件
建议导出为insert sql,并检查 name, code 值是否包含单引号’,将一个单引号’替换成两个单引号’,如’替换成’’,防止sql注入攻击。目标表修改为main_test_tmp
SELECT name, code FROM sla.slave_test WHERE code IS NOT NULL AND name IS NOT NULL
3、向main_test_tmp表插入文件中的sql
4、给main_test_tmp表name字段创建前缀索引
因为name字段长度为100,一些数据库对索引长度有限制,并且name字段的前10个字符唯一度已经很高
ALTER TABLE main_test_tmp ADD INDEX (name(10));
5、更新main_test_tmp表的test_id字段
UPDATE main_test_tmp mtt INNER JOIN main_test mt ON mtt.name = mt.name SET mtt.test_id = mt.id
WHERE mt.code IS NULL;
6、给main_test_tmp表test_id字段创建索引
注意,第6步只执行一次,以后不再执行
ALTER TABLE main_test_tmp ADD INDEX (test_id);
7、查询main_test_tmp表是否存在test_id字段不为null的数据
SELECT * FROM main_test_tmp WHERE test_id IS NOT NULL LIMIT 1;
如果存在,则继续下一步,否则执行第11步。
8、更新main_test表的code字段
UPDATE main_test mt INNER JOIN main_test_tmp mtt ON mt.id = mtt.test_id SET mt.code = mtt.code
WHERE mtt.test_id IS NOT NULL;
9、main_test_tmp表test_id字段都更新为null
UPDATE TABLE main_test_tmp SET test_id = null;
10、回到第5步,重复步骤(需要跳过第6步)
11、main_test表的code字段更新完毕,删除临时表main_test_tmp
DROP TABLE main_test_tmp;
说明
以上只考虑了main_test表name字段重复的情况。
Mysql更新百万历史数据相关推荐
- 新的mysql如何使用_如何使用新的MySQL更新日志
使用新的MySQL更新日志的方法未必人人都会,下面就教您如何使用新的MySQL更新日志的方法,希望对您能够有所帮助.如果你只使用一 使用新的MySQL更新日志的方法未必人人都会,下面就教您如何使用新的 ...
- mysql更新日志问题
[root@localhost ~]# /etc/init.d/mysqld restart 停止 mysqld: [确定] 正在启动 mysqld: [确定] 故障:今天在维护以前数据库日志的时候, ...
- mysql更新字符串中某个字符串_mysql更新某个字符串字段的部分内容
如果现在需要Mysql更新字段重部分数据,而不是全部数据,应该采用何种方法呢?下面介绍了两种情况下Mysql更新字段中部分数据的方法,供您参考. Mysql更新字段中部分数据第一种情况: update ...
- 如何给mysql表添加百万条数据_给mysql一百万条数据的表添加索引
直接alter table add index 添加索引,执行一个小时没反应,并且会导致锁表:故放弃该办法,最终解决办法如下: 一.打开mysql 命令行客户端 这里我们那可以看到导出的数据文件所存放 ...
- mysql更新多条数据6_mysql语句:批量更新多条记录的不同值
mysql更新语句很简单,更新一条数据的某个字段,一般这样写: 如果更新同一字段为同一个值,mysql也很简单,修改下where即可: 这里注意 'other_values' 是一个逗号(,)分隔的字 ...
- Mysql更新字段中部分数据的方法
如果现在需要Mysql更新字段重部分数据,而不是全部数据,应该采用何种方法呢?下面介绍了两种情况下Mysql更新字段中部分数据的方法,供您参考. Mysql更新字段中部分数据第一种情况: update ...
- mysql 条件触发器_具有条件的MySQL更新触发器(MySQL Update Trigger with Conditions)
具有条件的MySQL更新触发器(MySQL Update Trigger with Conditions) 我有一个PHP应用程序,通过TEST15将'Pass','Fail'或'NA'插入到字段TE ...
- MySQL更新行和插入列的语句
MySQL更新行和插入列的语句 1.修改表结构采用alter table语句.修改表结构指增加或删除字段.修改字段名称或字段类型.设置取消主键外键.设置取消索引以及修改表的注释等. 如:alter t ...
- Mysql 之百万数据导入
Mysql 之百万数据导入 1.方法 直接source sql 文件进行直接导入(不推荐) Load data infile命令进行导入(推荐) 更换引擎,将表的InnoDB引擎改为MyISAM,再导 ...
最新文章
- H5-Dooring可视化搭建平台的新技能
- 《敏捷软件开发》第二章极限编程实践
- forget password of WEBLOGIC user
- 使用Spring特性优雅书写业务代码
- FastReport使用方法(C/S版)
- VMware 常见使用问题梳理
- python分布式框架_高性能分布式执行框架——Ray
- python生成任意n阶的三对角矩阵
- java 动态实例化对象_记录Java中如何动态实例化一个对象
- 如何在SQL Server中自动进行表分区
- solr中facet及facet.pivot理解
- flink入门_Flink从入门到放弃-入门篇
- Pr 入门教程,如何在节目监视器中修剪剪辑?
- C语言-学生管理系统
- 乒乓球单循环赛_乒乓球单循环比赛如何计算得分排名(实用方法)
- 相见恨晚的一款前端布局神器!
- 离散小波变换wavedec matlab,MATLAB小波变换指令及其功能介绍(超级有用)
- 跨境电商国外消费者线上购物心理分析
- 计算机专业设计(论文)内容及要求,简述计算机专业毕业论文的撰写要求
- pcf8563c语言程序,PCF8563实时时钟C源程序