巧用CAS解决数据一致性问题

IT科技2025-11-04 00:01:5657457

在高并发的巧用分布式环境下,对于数据的解决数据查询与修改容易引发一致性问题,本文将分享一种非常简单但有效的性问优化方法。

一、巧用业务场景

业务场景为,解决数据购买商品的性问过程要对余额进行查询与修改,大致的巧用业务流程如下:

(1)从数据库查询用户现有余额 SELECT money FROM t_yue WHERE uid=$uid,不妨设查询出来的解决数据$old_money=100元

(2)业务层实施业务逻辑,比如购买一个80元的性问商品,并且打九折

if($old_money> 80*0.9) $new_money=$old_money-80*0.9=28

(3)将数据库中的巧用余额进行修改 UPDAtE t_yue SET money=$new_money WHERE uid=$uid

在并发量低的情况下,这个流程没有任何问题,解决数据原有金额100元,性问购买了80元的巧用九折商品(72元),剩余28元。解决数据

二、性问潜在的问题

在分布式环境中,如果并发量很大,这种“查询+修改”的业务很容易出现数据不一***限情况下,可能出现这样的异常流程:

(1)业务1和业务2同时查询余额,是100元

(2)业务1和业务2进行逻辑计算,免费信息发布网算出各自业务的余额,假设业务1算出的余额是28元,业务2算出的余额是38元

(3)业务1对数据库中的余额先进行修改,设置成28元。

业务2对数据库中的余额后进行修改,设置成38元。

此时异常出现了,原有金额100元,业务1扣除了72元,业务2扣除了62元,***剩余38元。

三、问题原因

高并发环境下,对同一个数据的并发读(两边都读出余额是100)与并发写(一个写回28,一个写回38)导致的数据一致性问题。

四、原因分析

业务1的写回:原有金额100,这是一个初始状态,写回金额28,理论上只有在原有金额为100的时候才允许写回成功,高防服务器这一步没问题。

业务2的写回:的原有金额100,这是一个初始状态,写回金额38,理论上只有在原有金额为100的时候才允许写回成功,可实际上,这个时候数据库中的金额已经变为28了,这一步的写操作不应该成功。

五、简易解决方案

在set写回的时候,加上初始状态的条件compare,只有初始状态不变时,才允许set写回成功,这正是大家常说的“Compare And Set”(CAS),是一种常见的降低读写锁冲突,保证数据一致性的方法。

六、业务的升级

业务线使用CAS解决高并发时数据一致性问题,只需要在进行set操作时,免费源码下载compare一下初始值,如果初始值变换,不允许set成功。

对于上文中的业务场景,只需要将“UPDAtEt_yue SET money=$new_money WHERE uid=$uid”升级为

“UPDAtE t_yue SETmoney=$new_money WHERE uid=$uid AND money=$old_money”即可。

并发操作发生时:

业务1执行 => UPDAtE t_yue SET money=28 WHERE uid=$uid AND money=100

业务2执行 => UPDAtE t_yue SET money=38 WHERE uid=$uid AND money=100

【这两个操作同时进行时,只能有一个执行成功】。

七、怎么判断哪个执行成功,哪个执行失败

set操作,其实无所谓成功或者失败,业务能通过affect rows得知哪个修改没有成功:

执行成功的业务,affect rows为1

执行失败的业务,affect rows为0

八、总结

高并发“查询并修改”的场景,可以用CAS(Compare and Set)的方式解决数据一致性问题。对应到业务,即在set的时候,加上初始条件的比对。

【本文为专栏作者“58沈剑”原创稿件,转载请联系原作者】

本文地址:http://www.bzve.cn/html/43d67699280.html
版权声明

本文仅代表作者观点,不代表本站立场。
本文系作者授权发表,未经许可,不得转载。

热门文章

全站热门

小米Note搭载MIUI8,为你带来怎样的使用体验?(深度探析MIUI8在小米Note上的亮点与优势)

系统->首选项->远程桌面

apt-get和apt-cache是Ubuntu Linux中的命令行下的包管理工具。 apt-get的GUI版本是Synaptic包管理器。该文中我们会展示apt-get和apt-cache命令的15个不同例子。示例:1 列出所有可用包复制代码代码如下:linuxtechi@localhost:~$ apt-cache pkgnames account-plugin-yahoojp ceph-fuse dvd+rw-tools e3 gnome-commander-data grub-gfxpayload-lists gweled .......................................示例:2 用关键字搜索包这个命令在你不确定包名时很有用,只要在apt-cache(LCTT 译注:这里原文是apt-get,应为笔误)后面输入与包相关的关键字即可。复制代码代码如下:linuxtechi@localhost:~$ apt-cache search web server apache2 - Apache HTTP Server apache2-bin - Apache HTTP Server (binary files and modules) apache2-data - Apache HTTP Server (common files) apache2-dbg - Apache debugging symbols apache2-dev - Apache HTTP Server (development headers) apache2-doc - Apache HTTP Server (on-site documentation) apache2-utils - Apache HTTP Server (utility programs for web servers) ......................................................................注意: 假如你安装了“apt-file”包,我们就可以像下面那样用配置文件搜索包。复制代码代码如下:linuxtechi@localhost:~$ apt-file search nagios.cfg ganglia-nagios-bridge: /usr/share/doc/ganglia-nagios-bridge/nagios.cfg nagios3-common: /etc/nagios3/nagios.cfg nagios3-common: /usr/share/doc/nagios3-common/examples/nagios.cfg.gz pnp4nagios-bin: /etc/pnp4nagios/nagios.cfg pnp4nagios-bin: /usr/share/doc/pnp4nagios/examples/nagios.cfg示例:3 显示特定包的基本信息复制代码代码如下:linuxtechi@localhost:~$ apt-cache show postfix Package: postfix Priority: optional Section: mail Installed-Size: 3524 Maintainer: LaMont Jones Architecture: amd64 Version: 2.11.1-1 Replaces: mail-transport-agent Provides: default-mta, mail-transport-agent .....................................................示例:4 列出包的依赖复制代码代码如下:linuxtechi@localhost:~$ apt-cache depends postfix postfix Depends: libc6 Depends: libdb5.3 Depends: libsasl2-2 Depends: libsqlite3-0 Depends: libssl1.0.0 |Depends: debconf Depends: cdebconf debconf Depends: netbase Depends: adduser Depends: dpkg ............................................示例:5 使用apt-cache显示缓存统计复制代码代码如下:linuxtechi@localhost:~$ apt-cache stats Total package names: 60877 (1,218 k) Total package structures: 102824 (5,758 k) Normal packages: 71285 Pure virtual packages: 1102 Single virtual packages: 9151 Mixed virtual packages: 1827 Missing: 19459 Total distinct versions: 74913 (5,394 k) Total distinct descriptions: 93792 (2,251 k) Total dependencies: 573443 (16.1 M) Total ver/file relations: 78007 (1,872 k) Total Desc/File relations: 93792 (2,251 k) Total Provides mappings: 16583 (332 k) Total globbed strings: 171 (2,263 ) Total dependency version space: 2,665 k Total slack space: 37.3 k Total space accounted for: 29.5 M示例:6 使用 “apt-get update” 更新仓库使用命令“apt-get update”, 我们可以重新从源仓库中同步文件索引。包的索引从“/etc/apt/sources.list”中检索。复制代码代码如下:linuxtechi@localhost:~$ sudo apt-get update Ign http://extras.ubuntu.com utopic InRelease Hit http://extras.ubuntu.com utopic Release.gpg Hit http://extras.ubuntu.com utopic Release Hit http://extras.ubuntu.com utopic/main Sources Hit http://extras.ubuntu.com utopic/main amd64 Packages Hit http://extras.ubuntu.com utopic/main i386 Packages Ign http://in.archive.ubuntu.com utopic InRelease Ign http://in.archive.ubuntu.com utopic-updates InRelease Ign http://in.archive.ubuntu.com utopic-backports InRelease ................................................................示例:7 使用apt-get安装包复制代码代码如下:linuxtechi@localhost:~$ sudo apt-get install icinga上面的命令会安装叫“icinga”的包。示例:8 升级所有已安装的包复制代码代码如下:linuxtechi@localhost:~$ sudo apt-get upgrade示例:9 更新特定的包在apt-get命令中的“install”选项后面接上“-only-upgrade”用来更新一个特定的包,如下所示:复制代码代码如下:linuxtechi@localhost:~$ sudo apt-get install filezilla --only-upgrade示例:10 使用apt-get卸载包复制代码代码如下:linuxtechi@localhost:~$ sudo apt-get remove skype上面的命令只会删除skype包,假如你想要删除它的配置文件,在apt-get命令中使用“purge”选项。如下所示:复制代码代码如下:linuxtechi@localhost:~$ sudo apt-get purge skype我们可以结合使用上面的两个命令:复制代码代码如下:linuxtechi@localhost:~$ sudo apt-get remove --purge skype示例:11 在当前的目录中下载包复制代码代码如下:linuxtechi@localhost:~$ sudo apt-get download icinga Get:1 http://in.archive.ubuntu.com/ubuntu/ utopic/universe icinga amd64 1.11.6-1build1 [1,474 B] Fetched 1,474 B in 1s (1,363 B/s)上面的目录会把icinga包下载到你的当前工作目录。示例:12 清理本地包占用的磁盘空间复制代码代码如下:linuxtechi@localhost:~$ sudo apt-get clean上面的命令会清空apt-get所下载的包占用的磁盘空间。我们也可以使用“autoclean”选项来代替“clean”,两者之间主要的区别是autoclean清理不再使用且没用的下载。复制代码代码如下:linuxtechi@localhost:~$ sudo apt-get autoclean Reading package lists... Done Building dependency tree Reading state information... Done示例:13 使用“autoremove”删除包当在apt-get命令中使用“autoremove”时,它会删除为了满足依赖而安装且现在没用的包。复制代码代码如下: linuxtechi@localhost:~$ sudo apt-get autoremove icinga示例:14 显示包的更新日志复制代码代码如下: linuxtechi@localhost:~$ sudo apt-get changelog apache2 Get:1 Changelog for apache2 (http://changelogs.ubuntu.com/changelogs/pool/main/a/apache2/apache2_2.4.10-1ubuntu1/changelog) [195 kB] Fetched 195 kB in 3s (60.9 kB/s)上面的命令会下载apache2的更新日志,并在你屏幕上分页显示。示例:15 使用 “check” 选项显示损坏的依赖关系复制代码代码如下:linuxtechi@localhost:~$ sudo apt-get check Reading package lists... Done Building dependency tree Reading state information... Done

有个领导想在自己安装了ubuntu的系统中装个打印机,我说行啊,我来帮你装,顺便就截了几张图,分享给大家步骤。网络打印机是有一个IP地址的哦!和共享打印机的添加方法不太一样,但是可以借鉴参考。1、打开菜单里面的设置按钮,对!就是桌面靠左,像齿轮的那个。点开它2、在 系统设置窗口中的“硬件”项目下面,找到“打印机”,并使用鼠标左键点开它。3、在打印机对话窗口里面,我们点击两个添加其中的一个。来添加一个打印机4、在选择设备下面,找到“网络打印机”一项,我并使用鼠标左键点击它5、被点开的“网络打印机”下面,一般情况会自动搜索到网络打印机,并且给你展示出来,如下图,Generic 21c-1(192.168.x.1) ,我们点中它,然后点击窗口中右下角处的“前进”6、我们选择ubuntu系统为我们查找到并且“推荐”的打印机类型,然后点击“前进”7、接下来的两个驱动程序,系统也会默认为您选择好,我们就保持它默认的“推荐”驱动就好了。继续点击“继续”按钮。8、在打印机描述中,你可以更改里面的数据,位置也可以改变,但是我这里都保持默认,直接点击“应用”按钮继续操作。9、接下来,系统会开始着手为您安装该网络打印机的驱动程序,等待安装完成后。会提示您是否打印一张测试页,根据你的需求点击即可,这样我们就安装好了网络打印机啦。

解决电脑显示dll文件错误的方法(如何修复电脑显示dll文件错误问题)

先来介绍一下硬盘分区的基本知识:物理介质 The physical media逻辑卷管理说明不幸的是,该磁盘工具不支持LVM的大多数强大的特性,没有管理卷组、扩展分区,或者创建快照等选项。对于这些操作,你可以通过终端来实现,但是没有那个必要。相反,你可以打开Ubuntu软件中心,搜索关键字LVM,然后安装逻辑卷管理工具,你可以在终端窗口中运行sudo apt-get install system-config-lvm命令来安装它。安装完之后,你就可以从dash上打开逻辑卷管理工具了。这个图形化配置工具是由红帽公司开发的,虽然有点陈旧了,但却是唯一的图形化方式,你可以通过它来完成上述操作,将那些终端命令抛诸脑后了。比如说,你想要添加一个新的物理卷到卷组中。你可以打开该工具,选择未初始化条目下的新磁盘,然后点击“初始化条目”按钮。然后,你就可以在未分配卷下找到新的物理卷了,你可以使用“添加到现存卷组”按钮来将它添加到“ubuntu-vg”卷组,这是Ubuntu在安装过程中创建的卷组。要扩展逻辑分区到物理空间,你可以在逻辑视图下选择它,点击编辑属性,然后修改大小来扩大分区。你也可以在这里缩小分区。system-config-lvm的其它选项允许你设置快照和镜像。对于传统桌面而言,你或许不需要这些特性,但是在这里也可以通过图形化处理。记住,你也可以使用终端命令完成这一切。

如何处理控件报文错误(解决电脑控件报文错误的方法与技巧)

前面两个经验我们准备好了安装Ubuntu15.04所需的工具和文件。一是下载好了Ubuntu15.04的系统镜像,需要注意的是通过官网下载,要到其英文官方网站上去下载最新的,假如是中文官网的话,可能内容较旧。二是我们通过Virtualbox新建好了一个虚拟机,我们可以将其理解成准备好了一台PC机。下面我们正式开始系统安装吧。软件名称:Ubuntu 14.04 官方正式版软件大小:752MB更新时间:2014-05-071、点击“Start”,打开虚拟机,启动系统安装。2、我们选择“Install Ubuntu”可以直接开始安装,也可以先试用,选择“Try Ubuntu”,然后再决定是否正式安装。此处,我们直接选择“Install Ubuntu”。3、此处我们需要注意的是:在安装Ubuntu桌面系统期间,最好断开网络,不然它会安装过程中连接互联网进行一些更新,这样会安装很慢。因此,我们断开网络。方法:在虚拟机右下角的网络图标上,选择断开。4、断开后,过一会,is connected to Internet 前面会变一个X字,表示网络已经断开。5、点击“Continue”继续,进入安装类型的选择,我们选择默认,“擦除磁盘并安装系统”,点击“Install Now”。6、需要确认,我们点击Continue继续。7、进入区域选择,我们选择Shanghai,或者直接输入Shanghai也是可以的。点击Continue。8、进入键盘布局配置,我们默认,继续Continue。9、进入用户配置。设置用户名和密码。点击Continue。10、此时就会进入安装界面了,我们可以来杯coffee了。11、安装成功。12、点击”Restart Now“,重启进入安装好的Ubuntu桌面系统。输入刚刚设置的密码,登录系统。

热门文章

友情链接

滇ICP备2023006006号-39