前言:

  • redis不仅仅是单纯的缓存,它还有一些特殊的功能,在一些特殊场景上很好用。
  • 本篇博文用来测试下使用redis来防止抢购商品超卖问题。

内容:

  • 使用redis的list进行测试

    思路是设置一个redis列表List,假设有十个商品,每次请求先判断List的长度,小于十就能抢到商品,将用户信息存放到List中。代码如下

 //进行抢购
protected function way_list(){
$num = $this->redis->lLen();
if($this->redis->lLen()>=self::AMOUNTLIMIT){
$this->writeLog("抢购失败".$num);
return;
}else{
$this->redis->rPush($num);
$this->writeLog("抢购成功".$num);
}
}

结果:失败!

可以很明显数量不对顺序也不对。

分析了下原因,在代码执行时,多用户并发请求时,第一个用户判断List长度符合条件还未进行List写入时,第二个用户也通过了List长度判断。所以就导致执行失败。

这就没有利用到redis的原子性

所以进行了改良

  • 使用redis 的incrby。incrby将制定key 的值增加指定的增量,并返回增量后的值。是一个原子性操作。所谓的原子性操作就是执行该方法后要嘛成功要嘛失败。

思路就是设置一个键值对存放被抢购数量,每次一个用户进来就将该值加一进行判断,如果小于抢购的商品数量则抢购成功,否则失败。代码如下

 protected function way_string(){
//判断是否有初始化
if(!$this->redis->exists(self::sold_name)){
$this->redis->setnx(self::sold_name,0);
}
if($this->redis->incrby(self::sold_name,1) > self::AMOUNTLIMIT){
$this->writeLog('失败');
}else{
$this->writeLog('成功');
}
}

结果

压力测试了几次都没有出现问题

通过apache自带的ab压力测试,进行五百次连接请求,并发三百次,没有出现超卖行为。

总结:会出现超卖主要是由于用户在请求的时候,代码在执行是有先后,会导致执行结果不符合预期。而采用redis的原子性就能避免。

使用redis防止抢购商品超卖的更多相关文章

  1. redis防止抢购商品超卖

    前言: redis不仅仅是单纯的缓存,它还有一些特殊的功能,在一些特殊场景上很好用. 本篇博文用来测试下使用redis来防止抢购商品超卖问题. 内容: 使用redis的list进行测试 思路是设置一个 ...

  2. 以商品超卖为例讲解Redis分布式锁

    本案例主要讲解Redis实现分布式锁的两种实现方式:Jedis实现.Redisson实现.网上关于这方面讲解太多了,Van自认为文笔没他们好,还是用示例代码说明. 一.jedis 实现 该方案只考虑R ...

  3. PHP+Redis链表解决高并发下商品超卖问题

    目录 实现原理 实现步骤 上一篇文章聊了一下使用Redis事务来解决高并发商品超卖问题,今天我们来聊一下使用Redis链表来解决高并发商品超卖问题. 实现原理 使用redis链表来做,因为pop操作是 ...

  4. PHP+Redis实现高并发下商品超卖问题

    对于一些有一定用户量的电商网站,如果只是单纯的使用关系型数据库(如MySQL.Oracle)来做抢购,对数据库的压力是非常大的,而且如果不使用好数据库的锁机制,还会导致商品.优惠券超卖的问题.我所在的 ...

  5. 【转】从msql数据库处理高并发商品超卖

    今天王总又给我们上了一课,其实mysql处理高并发,防止库存超卖的问题,在去年的时候,王总已经提过:但是很可惜,即使当时大家都听懂了,但是在现实开发中,还是没这方面的意识.今天就我的一些理解,整理一下 ...

  6. 使用 redis 减少 秒杀库存 超卖思路

    由于数据库查询的及插入的操作 耗费的实际时间要耗费比redis 要多, 导致 多人查询时库存有,但是实际插入数据库时却超卖 redis 会有效的减少相关的延时,对于并发量相对较少的 可以一用 publ ...

  7. redis分布式锁解决超卖问题

    redis事务 redis事务介绍:    1. redis事务可以一次执行多个命令,本质是一组命令的集合. 2.一个事务中的所有命令都会序列化,按顺序串行化的执行而不会被其他命令插入 作用:一个队列 ...

  8. 使用 redis 减少 秒杀库存 超卖思路 (转)

      由于数据库查询的及插入的操作 耗费的实际时间要耗费比redis 要多, 导致 多人查询时库存有,但是实际插入数据库时却超卖 redis 会有效的减少相关的延时,对于并发量相对较少的 可以一用 1 ...

  9. Redis 分布式锁使用不当,酿成一个重大事故,超卖了100瓶飞天茅台!!!(转)

    基于Redis使用分布式锁在当今已经不是什么新鲜事了. 本篇文章主要是基于我们实际项目中因为redis分布式锁造成的事故分析及解决方案.我们项目中的抢购订单采用的是分布式锁来解决的,有一次,运营做了一 ...

随机推荐

  1. ubuntu 中安装 ZED SDK 及结合ROS 的使用

    双目视觉(stereo vision),由于估计深度相对容易且稠密,在姿态估计和建图时容易初始化和估计尺度,所以在三维重建,SLAM等的应用中有这广泛的应用. ZED 作为近几年出现的商业化双目传感器 ...

  2. divide_3

    xiao方法 #include<stdio.h> #include<vector> #include<iostream> using namespace std; ...

  3. shiro实战系列(十五)之Spring集成Shiro

    Shiro 的 JavaBean 兼容性使得它非常适合通过 Spring XML 或其他基于 Spring 的配置机制.Shiro 应用程序需要一个具 有单例 SecurityManager 实例的应 ...

  4. PHP7.0新特性

    http://blog.csdn.net/h330531987/article/details/74364681 反射 闭包 trait 还有数组

  5. DataGridView如何绑定DataRow对象集合

    DataGridView对象是我们在进行Winform程序开发中经常使用的呈现数据的控件,而数据则是通过DataSource这个Property来设置的.根据MSDN的说明,DataGridView对 ...

  6. 八款开源 Android 游戏引擎 (巨好的资源)

    转载地址:http://software.intel.com/zh-cn/blogs/2012/01/13/android-4 初学Android游戏开发的朋友,往往会显得有些无所适从,他们常常不知道 ...

  7. mysql中left join中的on条件 和 where条件区别

    需要知道sql中关键字的执行顺序. FROM-> ON->JOIN-> WHERE->GROUP BY-> HAVING->SELECT-> DISTINCT ...

  8. 相亲神器记录Swift1.2

    这个简单APP是用swfit1.2写的,主要重点是:1.点击键盘return键可退出键盘. 2.各个控件值的传递. Storyboard界面设计: View代码: import UIKit class ...

  9. 【LeeCode88】Merge Sorted Array★

    1.题目描述: 2.解题思路: 题意:两个由整数构成的有序数组nums1和nums2,合并nums2到nums1,使之成为一个有序数组.注意,假设数组nums1有足够的空间存储nums1和nums2的 ...

  10. 20155222卢梓杰 实验九 Web安全基础

    实验九 Web安全基础 今天不多bb,打开webgoat就是干好吧 1.简单字符串sql注入 可以看到这个实验说明是 "下表允许用户查看其信用卡号码.尝试插入一个SQL字符串,以显示所有信用 ...