PHP开发中解决并发问题的几种实现方法分析


Posted in PHP onNovember 13, 2017

本文实例讲述了PHP开发中解决并发问题的几种实现方法。分享给大家供大家参考,具体如下:

对于商品抢购等并发场景下,可能会出现超卖的现象,这时就需要解决并发所带来的这些问题了

在PHP语言中并没有原生的提供并发的解决方案,因此就需要借助其他方式来实现并发控制。

方案一:使用文件锁排它锁

flock函数用于获取文件的锁,这个锁同时只能被一个线程获取到,其它没有获取到锁的线程要么阻塞,要么获取失败

在获取到锁的时候,先查询库存,如果库存大于0,则进行下订单操作,减库存,然后释放锁

方案二:使用Mysql数据库提供的悲观锁

Innodb存储引擎支持行级锁,当某行数据被锁定时,其他进程不能对这行数据进行操作

先查询并锁定行:

select stock_num from table where id=1 for update
if(stock_num > 0){
//下订单
update table set stock_num=stock-1 where id=1
}

方案三:使用队列

将用户的下单请求依次存入一个队列中,后台用一个单独的进程处理队列中的下单请求

方案四:使用Redis

redis的操作都是原子性的,可以将商品的库存存入redis中,下单之前对库存进行decr操作,如果返回的值大于等于0等可以下单,否则不能下单,这种方式效率较高

if(redis->get('stock_num') > 0){
 stock_num = redis->decr('stock_num')
 if(stock_num >= 0){
 //下订单
 }else{
 //库存不足
 }
}else{
//库存不足
}

其他并发问题:

在现实应用中,很多情况下会把数据存入缓存,当缓存失效时,去数据库取数据并重新设置缓存,如果这时并发量很大,会有很多进程同时去数据库取数据,导致很多请求

穿透到数据库,而使数据库奔溃,这里可用文件锁来解决

$data = $cache->get('key');
if(!$data){
  $fp = fopen('lockfile');
  if(flock($fp, LOCK_EX)){
    $data = $cache->get('key');//拿到锁后再次检查缓存,这时可能已经有了
    if(!$data){
      $data = mysql->query();
      $cache->set('key', $data);
    }
    flock($fp, LOCK_UN);
  }
  fclose($fp);
}

说白了,要解决并发问题就必须要加锁,各种方案的本质都是加锁

希望本文所述对大家PHP程序设计有所帮助。

PHP 相关文章推荐
解析PHP函数array_flip()在重复数组元素删除中的作用
Jun 27 PHP
保存到桌面、设为桌面且带图标的PHP代码
Nov 19 PHP
PHP中使用sleep造成mysql读取失败的案例和解决方法
Aug 21 PHP
PHP实现通过中文字符比率来判断垃圾评论的方法
Oct 20 PHP
php常见的魔术方法详解
Dec 25 PHP
php输出指定时间以前时间格式的方法
Mar 21 PHP
php实现随机生成易于记忆的密码
Jun 19 PHP
PHP使用SOAP扩展实现WebService的方法
Apr 01 PHP
Laravel重写用户登录简单示例
Oct 08 PHP
浅谈php和js中json的编码和解码
Oct 24 PHP
Laravel程序架构设计思路之使用动作类
Jun 07 PHP
thinkphp框架实现路由重定义简化url访问地址的方法分析
Apr 04 PHP
三个思路解决laravel上传文件报错:413 Request Entity Too Large问题
Nov 13 #PHP
kindeditor 加入七牛云上传的实例讲解
Nov 12 #PHP
Thinkphp5 微信公众号token验证不成功的原因及解决方法
Nov 12 #PHP
PHP 断点续传实例详解
Nov 11 #PHP
PHP+AJAX 投票器功能
Nov 11 #PHP
PHP实现双链表删除与插入节点的方法示例
Nov 11 #PHP
PHP实现基于栈的后缀表达式求值功能
Nov 10 #PHP
You might like
Linux安装配置php环境的方法
2016/01/14 PHP
php中引用符号(&)的使用详细介绍
2016/12/06 PHP
PHP命令空间namespace及use的用法小结
2017/11/27 PHP
使javascript也能包含文件
2006/10/26 Javascript
Extjs学习笔记之一 初识Extjs之MessageBox
2010/01/07 Javascript
Jquery中dialog属性小记
2010/09/03 Javascript
JQuery入门——用bind方法绑定事件处理函数应用介绍
2013/02/05 Javascript
jQuery实现跟随鼠标运动图层效果的方法
2015/02/02 Javascript
基于MVC4+EasyUI的Web开发框架形成之旅之界面控件的使用
2015/12/16 Javascript
jQuery仿写百度百科的目录树
2017/01/03 Javascript
JS实现数组深拷贝的方法分析
2019/03/06 Javascript
深入解析微信小程序开发中遇到的几个小问题
2020/07/11 Javascript
在vue中对数组值变化的监听与重新响应渲染操作
2020/07/17 Javascript
Python中的XML库4Suite Server的介绍
2015/04/14 Python
利用python批量检查网站的可用性
2016/09/09 Python
Python判断文件或文件夹是否存在的三种方法
2017/07/27 Python
Django组件之cookie与session的使用方法
2019/01/10 Python
Python Django Cookie 简单用法解析
2019/08/13 Python
Django关于admin的使用技巧和知识点
2020/02/10 Python
Python 窗体(tkinter)下拉列表框(Combobox)实例
2020/03/04 Python
Python docutils文档编译过程方法解析
2020/06/23 Python
pip/anaconda修改镜像源,加快python模块安装速度的操作
2021/03/04 Python
Grid 宫格常用布局的实现
2020/01/10 HTML / CSS
Perry Ellis官网:美国男士品味服装
2016/12/09 全球购物
美国生日蛋糕店:Bake Me A Wish!
2017/02/08 全球购物
中国跨境电子商务网站:NewFrog
2018/03/10 全球购物
Europcar西班牙:全球汽车租赁领域的领导者
2018/09/17 全球购物
什么是smarty? Smarty的优点是什么?
2013/08/11 面试题
北京某公司的.net笔试题
2014/03/20 面试题
护理专科毕业推荐信
2013/11/10 职场文书
工艺工程师工作职责
2013/11/23 职场文书
司法局群众路线教育实践活动整改措施
2014/09/17 职场文书
民用住房租房协议书
2014/10/29 职场文书
学校2015年纠风工作总结
2015/05/15 职场文书
2016高一新生军训心得体会
2016/01/11 职场文书
JS高级程序设计之class继承重点详解
2022/07/07 Javascript