批量进行Mysql数据处理的一项工作记录以及保存一个nginx变量大全

一、批量进行Mysql数据处理的一项工作记录

        在使用SQL执行一起数据批量处理的时候遇到执行数速度非常慢。表temp_users是一个包含百万级的用户ID表,表user_list是一个亿级的表,因为跨库,这里使用的是federated引擎创建的结构表。根据要实现的目标,理论上要执行的SQL应该如下:

update temp_users tu, user_list ul set tu.passwordss=ul.passwd, tu.mobiless=ul.mobile where tu.passwordss is null and tu.uidss=ul.uid;

但因为数据量太大,在直接执行这个SQL的时候发现半天没有响应,基本属于走不通的理论可行的逻辑(当然或许也和我本机性能较差)。当前情况下,只能着手进行优化处理。

【1.分步先批量取出uid批量修改数据】

        查询百万级表,一次取出几百条的用户ID,使用in查询从亿级表中取出要拿到的字段数据,然后组装成几百个SQL一次性扔给数据库执行修改,首先是这个方法是可行的,但速度大概在1秒10条左右,还是比较慢,全量修改完毕需要约3天时间。

【2.直接对uid分批执行SQL】

        在1方法太慢之后,我想了想其它的办法,其中之一就是将uid在SQL中进行分批以减少一次影响的数量。总共百万级,又涉及到跨库查询,在尝试按末尾一位、二位、三位后,发现三位执行时间还可以,且不易超时。如下:

update tv_users tu,user_list ul set tu.passwordss=ul.passwd, tu.mobiless=ul.mobile where SUBSTR(uidss,-3) = '100' and tu.passwordss is null and tu.uidss=ul.uid;
#受影响的行: 1521
#时间: 16.357s

        此方法确实可行。这样来看,一秒终大约能执行100条,是上面速度的10倍,应该在几个小时就能执行完毕。于是使用程序批量生成1000条SQL语句放在navicat查询下执行,

【3.使用存储函数替代批量执行】

        在2的方法凑效之后,可以考虑使用存储函数,就不需要再用程序批量生成一大堆的SQL,粘贴执行,使用存储函数更显得对MYSQL的熟练运用吧。存储函数如下:

delimiter //
drop procedure if exists doupdate;
create procedure doupdate()begin declare i int;#小于100的加前补0的逻辑set i = 100;repeat update tv_users tu,user_list ul set tu.passwordss=ul.passwd, tu.mobiless=ul.mobile where tu.passwordss is null and SUBSTR(uidss,-3) = i and tu.uidss=ul.uid;set i = i + 1;until i > 999end repeat;
end //
#调用函数
call doupdate()

【4.发现问题速度变慢】

        上面2,3都是可以使用的方法,且我在开始执行的时候也确实可行,速度也正常,但是在执行到后期发现速度越来越慢:

[SQL] update tv_users tu,user_list ul set tu.passwordss=ul.passwd, tu.mobiless=ul.mobile where tu.passwordss is null and SUBSTR(uidss,-3) = '302' and tu.uidss=ul.uid;
#受影响的行: 1514
#时间: 49.051s
[SQL]update tv_users tu,user_list ul set tu.passwordss=ul.passwd, tu.mobiless=ul.mobile where tu.passwordss is null and SUBSTR(uidss,-3) = '989' and tu.uidss=ul.uid;
#受影响的行: 1524
#时间: 162.145s
[SQL]update tv_users tu,user_list ul set tu.passwordss=ul.passwd, tu.mobiless=ul.mobile where tu.passwordss is null and SUBSTR(uidss,-3) = '990' and tu.uidss=ul.uid;
#受影响的行: 1510
#时间: 249.241s
[SQL]update tv_users tu,user_list ul set tu.passwordss=ul.passwd, tu.mobiless=ul.mobile where tu.passwordss is null and SUBSTR(uidss,-3) = '991' and tu.uidss=ul.uid;
#受影响的行: 1569
#时间: 331.324s

        在该表中,目前只有uidss有索引,但使用substr进行处理查询就没法用上uidss的主索引了(此处我进行了测试,其中还发现查询select count(*)的时候能用上这个主索引,但是查询具体字段的时候用不上)。我到是知道mysql里BTREE索引中到是有一个前缀索引,但是我这里的查询是需要对后缀进行索引才有用。当然我也可以脑洞大开想一下再加一列,这列数据刚好和uidss字段内容是反着等,从而加上索引,不过我暂时还不想去试验这个方法。

        为什么会越来越慢呢?从索引来看,此查询用不上什么索引,或者说我未建相关索引;从数据变化来看,执行到越后面,passwordss字段为null的行越来越少。其它的变化我看不出来,是不是可以推测导致查询变慢的原因是因为null字段的问题,即一开始都是大量的null的时候还好查,后面null行越为越少时查询越来越慢。NULL 并不是空值,而是要占用空间,所以mysql在进行比较的时候,NULL 会参与字段比较,所以对效率有一部分影响。在B树索引中不会存储NULL值,所以如果索引的字段可以为NULL,索引的效率会下降很多。当然我这里尚未对passwordss字段加索引,但鉴于此,于是我考虑将这个passwordss字段的null值全部替换成空然后对此字段加索引进行尝试。操作后进行查询效率如下: 

[SQL]update tv_users tu force index (passwordss),user_list ul set tu.passwordss=ul.passwd, tu.mobiless=ul.mobile where tu.passwordss ='' and  SUBSTR(uidss,-3) = '001' and tu.uidss=ul.uid ;
#受影响的行: 0
#时间: 36.331s
[SQL]update tv_users tu force index (passwordss),user_list ul set tu.passwordss=ul.passwd, tu.mobiless=ul.mobile where tu.passwordss ='' and  SUBSTR(uidss,-3) = '040' and tu.uidss=ul.uid ;
#受影响的行: 1589
#时间: 134.757s

【5.其它可考虑的方法】

        上面虽然有所改善,但也只能说是有一点点吧,甚至也可以说没有什么改善。然后又有了一些想法,

#创建视图,利用视图修改
create view nopassdata as SELECT uid,passwd,mobile from user_list where uid in (select uidss from tv_users where passwordss = SUBSTR(uidss,-3) = '999');
update tv_users left join nopassdata on uid=uidss set passwordss=passwd, mobiless=mobile where passwordss='' and SUBSTR(uidss,-3) = '104';
#会有报错:[Err] 1443 - The definition of table 'nopassdata' prevents operation UPDATE on table 'tv_users'.
#创建临时表,连接临时表进行操作
create temporary table nopasstable SELECT uid,passwd,mobile from user_list where uid in (select uidss from tv_users where passwordss = '');
#整合成一个SQL:
update tv_users left join (SELECT uid,passwd,mobile from user_list where uid in (select uidss from tv_users where passwordss = '' limit 10);
) as nopass on uid = uidss set passwordss=passwd, mobiless=mobile where passwordss='';
#提示报错[Err] 1235 - This version of MySQL doesn't yet support 'LIMIT & IN/ALL/ANY/SOME subquery' MySQL子查询不支持 limit
#于是再加一层嵌套
update tv_users left join (SELECT uid,passwd,mobile from user_list where uid in (select uidss from (select uidss from tv_users where passwordss = '' limit 10) as tea )
) as nopass on uid = uidss set passwordss=passwd, mobiless=mobile where passwordss='';

        写到这里,我里通过方法2已经完成了90%的数据更新了,不过所使用的方法我相信不是最优的方法,做个记录吧。

二、保存一个nginx变量大全

$arg_PARAMETER          如果在请求中设置了查询字符串,那么这个变量包含在查询字符串是GET请求PARAMETER中的值。
$args                   该变量的值是GET请求在请求行中的参数。
$binary_remote_addr     二进制格式的客户端地址
$body_bytes_sent        响应体的大小,即使发生了中断或者是放弃,也是一样的准确。
$content_length         该变量的值等于请求头中的Content-length字段的值
$cookie_COOKIE          该变量的值是cookie COOKIE的值
$document_root          该变量的值为当前请求的location(http,server,location,location中的if)中root指令中指定的值。
$document_uri           同$uri
$host                   该变量的值等于请求头中Host的值。如果Host无效时,那么就是处理该请求的server的名称。在下列情况中,$host变量的取值不同于$http_host变量。当请求头中的Host字段未指定(使用默认值)或者为空值,那么$host等于server_name指令指定的值。当Host字段包含端口是,$host并不包含端口号。另外,从0.8.17之后的nginx中,$host的值总是小写。
$hostname               有gethostname返回值设置机器名。
$http_HEADER            该变量的值为HTTP 请求头HEADER,具体使用时会转换为小写,并且将“——”(破折号)转换为"_"(下划线)。
$is_args                如果设置了$args,那么值为“?”,否则为“”
$limit_rate             该变量允许限制连接速率。
$nginx_version           当前运行的nginx的版本号
$query_string           同$args
$remote_addr            客户端的IP地址
$remote_user             该变量等于用户的名字,基本身份验证模块使用。
$remote_port             客户端连接端口
$request_filename       该变量等于当前请求文件的路径,有指令root或者alias和URI构成。
$request_body           该变量包含了请求体的主要信息。该变量与proxy_pass或者fastcgi_pass相关。
$request_body_file      客户端请求体的临时文件。
$request_completion     如果请求成功完成,那么显示“OK”。如果请求没有完成或者请求不是该请求系列的最后一部分,那么它的值为空。
$request_method         该变量的值通常是GET或者POST。
$request_uri            该变量的值等于原始的URI请求,就是说从客户端收到的参数包括了原始请求的URI,该值是不可以被修改的,不包含主机名,例如“/foo/bar.php?arg=baz”。
$scheme                 该变量表示HTTP scheme(例如HTTP,HTTPS),根据实际使用情况来决定,例如:rewrite  ^ $scheme://example.com$uri redirect;
$server_addr            该变量的值等于服务器的地址。通常来说,在完成一次系统调用之后就会获取变量的值,为了避开系统钓鱼,那么必须在listen指令中使用bind参数。
$server_name            该变量为server的名字。
$server_port            该变量等于接收请求的端口。
$server_protocol        该变量的值为请求协议的值,通常是HTTP/1.0或者HTTP/1.1
$uri                    该变量的值等于当前请求中的URI(没有参数,不包括$args)的值。它的值不同于request_uri,由浏览器客户端发送的request_uri的值。例如,可能会被内部重定向或者使用index。另外需要注意:$uri不包含主机名,例如 "/foo/bar.html"
当前URL= $scheme://$server_name/$url

 

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/pingmian/52788.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

每日一练【最大连续1的个数 III】

一、题目描述 给定一个二进制数组 nums 和一个整数 k,如果可以翻转最多 k 个 0 ,则返回 数组中连续 1 的最大个数 。 二、题目解析 本题同样是利用滑动窗口的解法。 首先进入窗口,如果是1,就直接让right,但是如果是…

SAP LE学习笔记07 - MM与WM跨模块收货到仓库的流程中 如何实现 先上架再入库

上一章讲了LE中收货的一些特殊情况: 1,MM模块收货时,特别移动指标来标识的物料直接产生TO 2,MM中直接收货到仓库的固定Storage Bin(棚番)上 SAP LE学习笔记06 - MM与WM跨模块收货到仓库的流程中 带特别移动指标的物料也可以直接…

Netflix Feign:微服务HTTP调用如何简化?

Netflix Feign:微服务HTTP调用如何简化? 1、什么是Netflix Feign?2、Feign的优点3、示例4、总结 💖The Begin💖点点关注,收藏不迷路💖 1、什么是Netflix Feign? Feign是一个声明式的…

备考AMC10美国数学竞赛2024:吃透1250道真题和知识点(持续)

有什么含金量比较高的初中生数学竞赛吗?美国数学竞赛AMC10是个不错的选择。那么,如何备考AMC10美国数学竞赛呢?做真题,吃透真题和背后的知识点是备考AMC8、AMC10有效的方法之一。 通过做真题,可以帮助孩子找到真实竞赛…

【智能排班系统】Hibernate Validator 参数校验

🎯导读:本文档介绍了参数校验的重要性及其在软件开发中的作用,强调了数据完整性、安全性、用户体验、系统稳定性及开发效率等方面的关键价值。文档详细阐述了Hibernate Validator这一流行的Java验证框架的使用方法,展示了如何利用…

异业联盟的巅峰之作!某店生活 两年百亿销售额!

大家好 我是一家软件开发公司的产品经理 吴军 最近有个爆火的商业模式 带动了三方消费 平台能赚到钱 消费者能省钱 商家也能获取到客源甚至还能赚钱 他究竟是怎么样做到三方都赚到钱的? 在当前经济形势下,许多消费者变得谨慎,减少了不必…

Git之2.5版本重要特性及用法实例(五十七)

简介: CSDN博客专家、《Android系统多媒体进阶实战》一书作者. 新书发布:《Android系统多媒体进阶实战》🚀 优质专栏: Audio工程师进阶系列【原创干货持续更新中……】🚀 优质专栏: 多媒体系统工程师系列…

【架构设计】安全架构设计

安全架构概述 在当今以计算机、网络和软件为载体的数字化服务几乎成为人类社会赖以生存的手段,与之而来的计算机犯罪呈现指数上升趋势,因此,信息的可用性、完整性、机密性、可控性和不可抵赖性等安全保障有位重要,为满足这些诉求&…

【测试】——开发模型与测试模型

📖 前言:在软件开发过程中,理解和应用合适的开发模型与测试模型至关重要。本文将详细介绍几种常见的开发模型,如瀑布模型、螺旋模型、增量模型和敏捷过程,以及测试模型如V模型和W模型。 目录 🕒 1. 开发模型…

Nginx: 使用KeepAlived配置实现虚IP在多服务器节点漂移及Nginx高可用原理

使用KeepAlived配置实现虚IP在多服务器节点漂移 1 )环境准备 2台 linux , 一主一备 节点1:192.168.184.30 CentOS 7 Master节点2:192.168.184.40 CentOS 7 BackupVIP 192.168.184.50 安装 KeepAlived, $ yum install keepalived 注意&#x…

时空图卷积网络:用于交通流量预测的深度学习框架-1

摘要 准确的交通预测对于城市交通控制和引导至关重要。由于交通流的高度非线性和复杂性,传统方法无法满足中长期预测任务的需求,且往往忽略了空间和时间的依赖关系。本文提出一种新的深度学习框架——时空图卷积网络(STGCN)来解决交通领域的时间序列预测…

云同步的使用

云同步技术是一种在多个设备或系统之间保持数据一致性的技术,它通常依赖于云存储服务来实现。在Java中,实现云同步功能通常需要与云服务提供商的API进行交互,如Amazon S3、Google Cloud Storage、Microsoft Azure Blob Storage等。 以下是一个…

golang gin template模板渲染

1、根据值控制html元素显示隐藏 main.go package main import ("html/template""net/http""github.com/gin-gonic/gin" ) func main() {r : gin.Default()r.SetFuncMap(template.FuncMap{"greaterThan": func(a, b int) bool {retur…

PyCharm 自定义字体大小

常用编程软件自定义字体大全首页 文章目录 前言具体操作1. 打开设置对话框2. 设置编辑器字体3. 选择外观字体 前言 PyCharm 自定义字体大小,统一设置为 JetBrains Mono 具体操作 【File】>【Settings...】>【Editor】>【Font】 统一设置为字体样式 JetB…

人工智能训练师工作内容及职业发展路径

人工智能训练师(AI Trainer)是一种专业职位,主要负责训练和优化人工智能系统,尤其是机器学习模型。他们的工作涉及到以下几个方面: 1、数据准备:训练师需要收集、清洗和预处理数据,以确保数据的…

C++ | Leetcode C++题解之第355题设计推特

题目&#xff1a; 题解&#xff1a; class Twitter {struct Node {// 哈希表存储关注人的 Idunordered_set<int> followee;// 用链表存储 tweetIdlist<int> tweet;};// getNewsFeed 检索的推文的上限以及 tweetId 的时间戳int recentMax, time;// tweetId 对应发送…

简易STL实现 | Deque的实现

一种 在内存中存储元素的数据结构&#xff0c;它支持 在两端添加和删除元素&#xff08;使用循环数组实现&#xff09; 1、deque的特性&#xff08;分段deque实现&#xff09; 1、双端操作&#xff1a; deque支持在前端和后端执行快速的插入和删除操作 2、随机访问&#xff…

Servlet 简介+ Cookie和session+过滤器Filter和监听器Listener

目录 1.Servlet 介绍 1.1 什么是Servlet 1.2 Servlet的使用方法 1.3 Servlet接口的继承结构 2.Servlet的生命周期 2.1 servlet生命周期中重要的方法 3.获得前端提交数据 4.中文乱码的解决方案 5.重定向和转发 5.1 重定向 5.2 转发 6. Request对象 7. Response对象…

Linux上启动redis

1.默认启动方式:在系统的任意位置执行 redis-server即可启动 ps:这是前端界面启动&#xff0c;无法直接连接redis&#xff0c;想要连接的话只能另外启动一个窗口&#xff0c;因此下面我们介绍后台启动redis 2.指定配置启动&#xff1a; redis的配置文件位置&#xff1a…

华为手机数据丢失如何恢复?

在智能手机普及的今天&#xff0c;华为手机凭借其卓越的性能和用户体验赢得了众多用户的青睐。然而&#xff0c;在使用过程中&#xff0c;我们难免会遇到数据丢失或误删除的情况。面对这一困境&#xff0c;许多用户可能会感到束手无策。别担心&#xff0c;本文将为你提供一份全…