位置: 编程技术 - 正文

Redis构建分布式锁(redis如何实现分布式事务)

编辑:rootadmin

推荐整理分享Redis构建分布式锁(redis如何实现分布式事务),希望有所帮助,仅作参考,欢迎阅读内容。

文章相关热门搜索词:redis做分布式,redis 分布式数据库,redis分布式搭建,redis分布式存储方案,redis如何实现分布式事务,redis分布式解决方案,redis分布式集群部署,redis如何实现分布式事务,内容如对您有帮助,希望把文章链接给更多的朋友!

1、前言

为什么要构建锁呢?因为构建合适的锁可以在高并发下能够保持数据的一致性,即客户端在执行连贯的命令时上锁的数据不会被别的客户端的更改而发生错误。同时还能够保证命令执行的成功率。

看到这里你不禁要问redis中不是有事务操作么?事务操作不能够实现上面的功能么?

的确,redis中的事务可以watch可以监控数据,从而能够保证连贯执行的时数据的一致性,但是我们必须清楚的认识到,在多个客户端同时处理相同的数据的时候,很容易导致事务的执行失败,甚至会导致数据的出错。

在关系型数据库中,用户首先向数据库服务器发送BEGIN,然后执行各个相互一致的写操作和读操作,最后用户可以选择发送COMMIT来确认之前的修改,或者发送ROLLBACK进行回滚。

在redis中,通过特殊的命令MULTI为开始,之后用户传入一连贯的命令,最后EXEC为结束(在这一过程中可以使用watch进行监控一些key)。进一步分析,redis事务中的命令会先推入队列,等到EXEC命令出现的时候才会将一条条命令执行。假若watch监控的key发生改变,这个事务将会失败。这也就说明Redis事务中不存在锁,其他客户端可以修改正在执行事务中的有关数据,这也就为什么在多个客户端同时处理相同的数据时事务往往会发生错误。

2、简单理解redis的单线程IO多路复用

Redis采用单线程IO多路复用模型来实现高内存数据服务。何为单线程IO多路复用呢?从字面的意思可以知道redis采用的是单线程、使用的是多个IO。整个过程简单的来讲就是,哪个命令的数据流先到达就先执行。

请看下面的形象理解图:图中是一座窄桥,只能允许一辆车通过,左边是车辆进入的通道,哪一辆车先到达就先进入。即哪个IO流先到达就先处理哪个。

Linux下网络IO使用socket套接字来通讯,普通IO模型只能监听一个socket,而IO多路复用可同时监控多个socket。IO多路复用避免阻塞在IO上,单线程保存多个socket的状态后轮循处理。

3、并发测试

我们就模拟一个简单典型的并发测试,然后从这个测试中得出问题,再进一步研究。

并发测试思路:

1、在redis中设置一个字符串count,运用程序将其取出来加+1,再存储回去,一直循环十万次

2、在两个浏览器上同时执行这个代码

3、将count取出来,查看结果

测试步骤:

1、建立test.php文件

2、分别在两个浏览器中访问test.php文件

结果由上图可知,总共执行两次,count原本应该是二十万才对的,但实际上count等于十三万多,远远小于二十万,这是为什么呢?

由前面的内容可知,redis是采用单线程IO多路复用模型的。因此我们使用两个浏览器即为两个会话(A、B),取出、加1、存入这三个命令并不是原子操作,并且在执行取出、存入这两个redis命令时是哪个客户端先到就先执行。

例如:

1、此时count=

2、A取出count=,紧接着B的取出命令流到了,也将count=取出

3、A取出后立即加1,并将count=存回去

4、此时B也紧跟着,也将count=存进去了

Redis构建分布式锁(redis如何实现分布式事务)

注意:

1、设置循环次数尽量大一点,太小的话,当在第一个浏览器执行完毕,第二个浏览器还没开始进行呢

2、必须要两个浏览器同时执行。假若在一个浏览器中同时执行两次test.php文件,不管是否同时执行,最终结果就是count=。因为在同一个浏览器中执行,都是属于同一个会话(所有命令都在同一个通道通过),所以redis会让先执行的十万次执行完,再接着执行其他的十万次。

4、事务解决与原子性操作解决

4.1、事务解决

更改后的test.php文件

执行结果失败,表名使用事务不能够解决此问题。

分析原因:

我们都知道当redis开启时,事务中的命令是不执行的,而是先将命令压入队列,然后当出现exec命令的时候,才会阻塞式的将所有的命令一个接一个的执行。

所以当使用PHP中的Redis类进行redis事务的时候,所有有关redis的命令都不会真正的执行,而仅仅是将命令发送到redis中进行存储起来。

因此下图中所圈到的$count实际上不是我们想要的数据,而是一个对象,因此test.php中行出错。

查看对象count:

4.2、原子性操作incr解决

#更新test.php文件

两个浏览器同时执行,耗时、秒,count=,可以解决此问题。

缺点:

仅仅只是解决这里的取出加1的问题,本质上还是没能解决问题的,在实际环境中,我们需要做的是一系列操作,不仅仅只是取出加1,因此就很有必要构建一个万能锁了。

5、构建分布式锁  

我们构造锁的目的就是在高并发下消除选择竞争、保持数据一致性

构造锁的时候,我们需要注意几个问题:

1、预防处理持有锁在执行操作的时候进程奔溃,导致死锁,其他进程一直得不到此锁

2、持有锁进程因为操作时间长而导致锁自动释放,但本身进程并不知道,最后错误的释放其他进程的锁

3、一个进程锁过期后,其他多个进程同时尝试获取锁,并且都成功获得锁

我们将不对test.php文件修改了,而是直接建立一个相对比较规范的面向对象Lock.class.php类文件  

#建立Lock.class,php文件

测试结果:

在两个不同的浏览器中执行,最终结果count=,但是耗时相对较多,需要近八十多秒左右。但是在高并发下,对同一个数据,二十万次上锁执行释放锁的操作还是可以接受的,甚至已经很不错了。

以上的简单例子仅仅只是为了模拟并发测试并检验而已,实际上我们可以使用Lock.class.php中的锁结合自己的项目加以修改就可以很好地使用这个锁了。例如商城中的疯狂抢购、游戏中虚拟商城玩家买卖东西等等。

标签: redis如何实现分布式事务

本文链接地址:https://www.jiuchutong.com/biancheng/293392.html 转载请保留说明!

上一篇:谈谈从phpinfo中能获取哪些值得注意的信息(请简述你对php的理解并描述php的工作流程)

下一篇:PHP获取当前日期及本周一是几月几号的方法(php获取当前时间戳函数)

  • 无效产权转移的契税需要征收吗?
  • 中级税务师是什么
  • 银行开具的票据有哪些
  • 个体工商户生产经营所得税税率表2021
  • 报销人和经办人怎么区分
  • 税控盘抵减增值税需要结转吗
  • 单一窗口报关单
  • 工程收入开票
  • 电子发票密码区显示不全
  • 增值税专用发票使用规定 最新
  • 行政单位要考什么
  • 之前付过款回来收到发票应该怎么做凭证
  • 月末应付职工薪酬计算方法
  • 公司账户没有钱怎么办
  • 包装报废会计处理
  • 公益捐赠税前扣除凭证
  • 税率简并的影响因素
  • 取得甲供材料按简易征收发票能抵扣吗
  • 企业代扣代缴个人所得税系统
  • steam打开速度
  • 旅游业小规模差额计税的能开1%
  • win 7怎么办
  • 房地产企业纳税申报需要报哪些报表
  • centos apache配置文件
  • 工程暂估收入入账的会计分录
  • 退回以前年度多交增值税
  • 出口退税一般退什么税
  • 个人所得税的征收模式为()A分类征收B综合征收C
  • 苏格兰高地牛一个萌萌哒的合集
  • 贴现资金是信贷资金吗
  • 建筑行业施工规范有哪些
  • php连接mysql数据库四步
  • 发生的计提费用没有发生怎么办
  • 与资产相关的政府补助有哪些
  • html导航栏边框
  • php网站用什么软件修改
  • 应收账款保理会计处理相关会计准则
  • 邮寄的发票对方没收到怎么办
  • PHPCMS 是 ThinkPHP 开发的吗?
  • 织梦痣铃表情太到位
  • 综合所得年度自行申报怎么操作
  • 预计净残值影响营业利润吗
  • 企业筹建期间可以上市吗
  • 主营业务成本和营业成本的区别
  • 民办非盈利组织注销了在哪登报
  • 咨询服务业主营业务成本
  • 对账结算流程
  • 存货价值的计算公式
  • 基建期罚款支出账务处理
  • 银行结息交易是扣钱的意思吗
  • 暂估入库有时间限制吗
  • 关于单独计价的规定
  • 凭证过账的步骤
  • 营业费用这个科目还在用吗
  • 母公司及子公司增资
  • 国税一证通
  • 旅游饮食服务企业会计核算的特点包括
  • mysql优化十大技巧
  • windows server 2008图片文件无法显示缩略图的解决方法
  • 鼠标右键一直锁定一个应用
  • ubuntu系统中文件夹不能改名
  • dwm.exe占用内存过高怎么办
  • vlcplayer最新版
  • linux系统问题汇总
  • cocos2dx小游戏
  • 微信小程序表单制作代码
  • innertext赋值
  • 商务英语考英语笔译 算跨考吗
  • list嵌套list采用什么结构
  • linux搭建ftp服务器
  • pythone爬虫
  • nodejs web服务器
  • unity视频播放
  • jquery audio
  • python 遍历数组
  • CLASS_CONFUSION JS混淆 全源码
  • 怎样查看招聘信息
  • 三门峡哪个小区是原火葬场
  • 网上订机票怎么取票
  • 北京买新车购置税怎么算
  • 免责声明:网站部分图片文字素材来源于网络,如有侵权,请及时告知,我们会第一时间删除,谢谢! 邮箱:opceo@qq.com

    鄂ICP备2023003026号

    网站地图: 企业信息 工商信息 财税知识 网络常识 编程技术

    友情链接: 武汉网站建设