MySQL更新字段来自另一个表的count()值
假设有文章post
和评论comment
两个表,文章表记录有评论的数量,但是这个值我们要一次更新。
如下,现在post表的comment_count
都是0
,我们的目标是:执行一个SQL语句,让其把统计comment
表的数据数量。
post
表数据如下:
+---------+-------------------+---------------+
| post_id | title | comment_count |
+---------+-------------------+---------------+
| 1 | How to lean MySQL | 0 |
| 2 | How to lean PHP | 0 |
| 3 | How to lean Redis | 0 |
+---------+-------------------+---------------+
comment
表数据如下:
+------------+---------+---------+
| comment_id | post_id | content |
+------------+---------+---------+
| 1 | 1 | Good! |
| 2 | 1 | Nice! |
| 3 | 1 | Yeap! |
+------------+---------+---------+
因为这里只有post_id=1
的文章有评论,所以最终的comment_count
值分别为:3 0 0
。
1 使用SQL语句
在数据量为100W以下的时候,可以用一条命令解决:
UPDATE post AS a SET comment_count = (select count(*) FROM comment WHERE post_id=a.post_id);
2 使用存储过程(数据量巨大时用)
当数据量很大的时候,比如1亿条记录,如果再用上面这条命令,就会导致所有行被锁定(InnoDB存储引擎)。
UPDATE
语句首先会查找需要更新的行,如果符合要求,先锁定,然后再更新,
上面这条语句会锁定所有行,等效于锁定全表。
解决这个问题的办法就是,按post
表的post_id
范围批量更新,具体代码如下:
DROP PROCEDURE IF EXISTS UpdateCount; DELIMITER //
CREATE PROCEDURE UpdateCount()
BEGIN
DECLARE lower INT; # ID下限
DECLARE upper INT; # ID上限
DECLARE step INT; # 次增加步数
DECLARE max_id INT; # 最大ID SET lower = 1;
SET upper = 0;
SET step = 10000; # 每次更新1万条数据
SET max_id = 0; # 从库中读取最大ID
SELECT max(post_id) INTO max_id FROM post; WHILE lower <= max_id DO
# 上限等于下限加上步宽
SET upper = lower + step; # 还是和上面的方法一样,只是多了post_id的限定范围
UPDATE post AS a
SET comment_count = (SELECT count(*) FROM comment WHERE post_id=a.post_id)
WHERE post_id >= lower and post_id < upper; # 更新下限
SET lower = upper;
END WHILE;
END;
//
DELIMITER ;
最后,调用一遍这个存储过程
call UpdateCount();
每次会更新1万条数据,也就是更新时暂时锁住这1万条,
一般来说,更新1万条数据执行也是很快的,
所以这样就避免了整表所有记录被锁的问题。
MySQL更新字段来自另一个表的count()值的更多相关文章
- mysql更新字段值提示You are using safe update mode and you tried to update a table without a WHERE that uses a KEY column To disable safe mode
1 引言 当更新字段缺少where语句时,mysql会提示一下错误代码: Error Code: 1175. You are using safe update mode and you tried ...
- Mysql JSON字段提取某一个属性值的函数
mysql从5.7开始才支持JSON_EXTRACT等 JSON相关的函数, 项目里用到的mysql是5.6的,需要提取JSON字段里某一个属性值进行统计, 自己写了一个笨的提取方法: CREATE ...
- MySQL 更新走全表和索引的评估记录数
#!/usr/bin/perl use DBI; $db_name='scan'; $ip='127.0.0.1'; $user="root"; $passwd="123 ...
- mysql查询字段所在表
use information_schema;select * from columns where column_name='字段名' ;
- mysql 查询字段为空显示默认值
IFNULL() 函数用于判断第一个表达式是否为 NULL,如果为 NULL 则返回第二个参数的值,如果不为 NULL 则返回第一个参数的值. IFNULL() 函数语法格式为: IFNULL(exp ...
- mysql更新字段内容
update article set a_content = REPLACE(`a_content`,'www.abc.com','www.bcd.com')
- mysql更新某个字符串字段的部分内容
如果现在需要Mysql更新字段重部分数据,而不是全部数据,应该采用何种方法呢?下面介绍了两种情况下Mysql更新字段中部分数据的方法,供您参考. Mysql更新字段中部分数据第一种情况: update ...
- MySQL数据库 字段操作 多表关系(更新中...)
外键 (foreign key) ## 外键 ```mysql # 作者(author):id,name,sex,age,mobile, detail_id # 作者详情(author_detail) ...
- 如何使用MySQL一个表中的字段更新另一个表中字段
[本文出自:https://www.jb51.net/article/150323.htm] 这篇文章主要介绍了如何使用MySQL一个表中的字段更新另一个表中字段,需要的朋友可以参考下 1,修改1列 ...
随机推荐
- Ceph osd故障硬盘更换
正常状态: 故障状态: 实施更换步骤: (1)关闭ceph集群数据迁移: osd硬盘故障,状态变为down.在经过mod osd down out interval 设定的时间间隔后,ceph将其标记 ...
- 利用netsh命令设置IP地址/DNS服务器地址
一.设置IP地址 1. 自动获取IP地址: netsh interface ip set address [name=]"本地连接" [source=]dhcp 2. 手动设置IP ...
- socket之UDP协议,并发编程介绍,操作系统发展史
socket之UDP协议 1.UDP协议 UDP 是User Datagram Protocol的简称, 中文名是用户数据报协议,是OSI(Open System Interconnection 参考 ...
- div随着屏幕滚动而滚动
<script type="text/javascript"> $(document).ready(function () { var menuYloc = $(&qu ...
- [爬虫] BeautifulSoup库
Beautiful Soup库基础知识 Beautiful Soup库是解析xml和html的功能库.html.xml大都是一对一对的标签构成,所以Beautiful Soup库是解析.遍历.维护“标 ...
- Fiddler-打断点(bpu)
一.断点 1.为什么要打断点? 比如一个购买的金额输入框,输入框前端做了限制大于100,那么我们测试的时候,需要测试小于100的情况下.很显然前端只能输入大于100的.这时我们可以先抓到接口,修改请求 ...
- Git及码云学习总结
前言 一.Git是一个版本管理工具软件. 二.windows 系统的使用: 1.git软件的安装:https://git-scm.com/downloads mac系统是自带的不用安装 windows ...
- Python学习【day04】- Python基础(集合、函数)
集合 #!/usr/bin/env python # -*- coding:utf8 -*- # set集合 只可放不可变的数据类型,本身是可变数据类型,无序 # s = {1,2,3,[1,2,3] ...
- js执行多次事件,而非一次
晚上查阅了很多文章,都是避免点击事件多次执行.反过来要是让事件多次执行该如何做? 这里可以配个setTimeout():来执行 这里我们用layui <link rel="styles ...
- PB中的DataStore的应用示例
编程过程中想在窗口中加一个下拉列表(DDLB),原来听同学说过可以动态改变下拉列表的值,数据库中的表改变,前台客户端的下拉列表就会变,记得当时同学说的是用一个叫下拉数据窗口(DDDW)的东西做的,一直 ...