redis队列的实现
redis中文官网:http://www.redis.cn/
关于redis队列的实现方式有两种:
1、生产者消费者模式。
2、发布者订阅者模式。
详解:
1、生产者消费者模式。
普通版本:
比如一个队列里面,生产者A push了一个数据进去,消费者B pop 了这个数据,那个这个队列依旧为空。所以是一对一的。
至于是先进先出还是先进后出等,可以依照函数lpush(从队列左边,也就是队首push一个数据) rpush(从队列右边也就是队尾push一个数据) lpop(同理) rpop等来控制。
插入数据:
显示数据:
取出数据:
阻塞版本:
但是上面的命令都是立即返回的,无论数据有无,关于取数据lpop有个增强版本,blpop(block left pop)阻塞版本,
使用方法:blpop key1 key2 ... keyn 10
同时预获取多个key的值,并设置超时时间为10s,如果所有key,有些key有value就立即返回,如果所有key都没有value就阻塞10秒返回
关于blpop多个key返回数据的顺序,比如blpop mylist mylist2 5这个命令,先检查mylist有数据就返回,如果没有数据,就检查mylist2依次。。。。直到所有key检查完如果都没有数据就阻塞。
这种从多个队列里面取数据的方式可以用来做优先级的队列,比如mylist队列的优先级高于mylist2,push的时候,高优先级就push到mylist里面,普通优先级就push到mylist2里面,
这样就会先取mylist里面的高优先级的数据来处理。
但是,如果遇到队列的优先级等级过多,比如有(0-9999)个优先级,上面就不行了。解决思路是插入的时候先把数据取出来自己实现二分查找找出该插入的位置,用lset命令插入。
如果数据过多,比如队列有几十万,可以把队列分成几十个或几百个小队列,比如0号队列存优先级为(0-1000),1号队列存优先级为(1001-2000)的数据,依次。。。。。
由于这种队列模式pop出来一个后就返回了,所以处理业务的时候最好把pop写在一个while(true){pop.....do logic}循环里面。
2、发布者订阅者模式
概念:
三个用户A,B,C同时都订阅了一个channel名字叫msg,然后发布者往msg的channel里面发布了一个数据,那么A,B,C三个用户都会收到该数据。
注意:
1、很明显,三个用户ABC需要阻塞。怎么收到订阅的数据呢,肯定是依靠注册在redis里面的回调函数。
2、发布的数据不会在redis里面复现,意思就是发布了以后,A,B,C由于种种原因没收到就没收到。。。。
直接上代码:
发布者:
$redis = new Redis();
$re = $redis->connect('127.0.0.1','6379');
// var_dump($re);exit; $type = 'msg';
$msg = "fuck sem"; $result = $redis->publish($type , $msg); //同步操作,第一个参数是channel,第二个参数是数据 if (empty($result)) {
echo 'publish failed';
}else{
echo 'publish success';
}
订阅者:
$redis = new Redis();
$redis->connect('127.0.0.1','6379');
$redis->setOption(\Redis::OPT_READ_TIMEOUT, - 1 );
//重点!!!得设置不timeout,否则60内没收到发布者的消息就会自动断开
$type = 'msg';
$msg = "fuck sem"; // $result = $redis->publish($type , $msg); $result = $redis->subscribe(array($type) , 'callback'); //异步阻塞,有消息来自动调用callback函数 function callback($redis , $type , $msg){
//这里处理逻辑
echo $type."==>". $msg."\r\n";
}
两种方式比较:
1、生产者消费者模式需要 消费者主动去拉数据,如果写成死循环并且阻塞模式,就和第二种方式差不多了。
2、发布者订阅者模式的数据并不存在于某个key里面,如果订阅者没收到则该数据就丢失了。
redis队列的实现的更多相关文章
- [bigdata] 使用Redis队列来实现与机器无关的Job提交与执行 (python实现)
用例场景: 定时从远程多台机器上下载文件存入HDFS中.一开始采用shell 一对一的方式实现,但对于由于网络或者其他原因造成下载失败的任务无法进行重试,且如果某台agent机器down机,将导致它对 ...
- 我心中的核心组件~MSMQ与Redis队列
回到目录 这个文章其实是我心中的核心组件的第七回,确实在时间上有些滞后了,但内容并不滞后!本文MSMQ只是个引题,我确实不太想说它,它是微软自己集成的一套消息队列,寄宿在Window服务里,稳定性十在 ...
- c#之Redis队列在邮件提醒中的应用
场景 有这样一个场景,一个邮件提醒的windows服务,获取所有开启邮件提醒的用户,循环获取这些用户的邮件,发送一条服务号消息.但问题来了,用户比较少的情况下,轮询一遍时间还能忍受,如果用户多了,那用 ...
- c#之Redis队列
摘要 这两天一直在考虑redis队列:一个生产者,多个消费者的情况,这里弄了一个demo进行测试. 一个例子 关于如何引用Redisclient 可以参考之前的这篇文章:c#之Redis实践list, ...
- (3)redis队列功能
Redis队列功能介绍 List 常用命令: Blpop删除,并获得该列表中的第一元素,或阻塞,直到有一个可用 Brpop删除,并获得该列表中的最后一个元素,或阻塞,直到有一个可用 Brpoplpus ...
- 转载:【高并发简单解决方案 | 靠谱崔小拽 】redis队列缓存 + mysql 批量入库 + php离线整合
需求背景:有个调用统计日志存储和统计需求,要求存储到mysql中:存储数据高峰能达到日均千万,瓶颈在于直接入库并发太高,可能会把mysql干垮. 问题分析 思考:应用网站架构的衍化过程中,应用最新的框 ...
- redis 队列缓存 + mysql 批量入库 + php 离线整合
问题分析 思考:应用网站架构的衍化过程中,应用最新的框架和工具技术固然是最优选择:但是,如果能在现有的框架的基础上提出简单可依赖的解决方案,未尝不是一种提升自我的尝试. 解决: 问题一:要求日志最好入 ...
- PHP电商订单自动确认收货redis队列
一.场景 之前做的电商平台,用户在收到货之后,大部分都不会主动的点击确认收货,导致给商家结款的时候,商家各种投诉,于是就根据需求,要做一个订单在发货之后的x天自动确认收货.所谓的订单自动确认收货,就是 ...
- 【高并发简单解决方案】redis队列缓存 + mysql 批量入库 + php离线整合
需求背景:有个调用统计日志存储和统计需求,要求存储到mysql中:存储数据高峰能达到日均千万,瓶颈在于直接入库并发太高,可能会把mysql干垮. 问题分析 思考:应用网站架构的衍化过程中,应用最新的框 ...
随机推荐
- 【支付专区】之对字符串数据进行Base64位加密,解密
加密,解密 String pwd="测试"; byte[] bytes = pwd.getBytes("UTF-8"); //加密 String pwdNew= ...
- 发送短信(string转换为JSON)
using Newtonsoft.Json;using System;using System.Collections.Generic;using System.Linq;using System.T ...
- C#_GDI+详细教程(图形图像编程基础)
第7章 C#图形图像编程基础 本章主要介绍使用C#进行图形图像编程基础,其中包括GDI+绘图基础.C#图像处理基础以及简单的图像处理技术. 7.1 GDI+绘图基础 编写图形程序时需要使用GDI( ...
- Chapter7: question 49 - 50
49. 把字符串转换为整数 很多细节需要注意.(空格,符号,溢出等) Go: 8. String to Integer (atoi) 50. 树种两个结点的最低公共祖先 A. 若是二叉搜索树,直接与根 ...
- 67. Container With Most Water
Container With Most Water Given n non-negative integers a1, a2, ..., an, where each represents a poi ...
- 安卓:drawable
<?xml version="1.0" encoding="utf-8"?> <shape xmlns:android="http: ...
- Laxcus大数据管理系统单机集群版
Laxcus大数据管理系统是我们Laxcus大数据实验室历时5年,全体系全功能设计研发的大数据产品,目前的最新版本是2.1版本.从三年前的1.0版本开始,Laxcus大数据系统投入到多个大数据和云计算 ...
- SQL注入原理
随着B/S模式应用开发的发展,使用这种模式编写应用程序的程序员也越来越多.但是由于这个行业的入门门槛不高,程序员的水平及经验也参差不齐,相当大一 部分程序员在编写代码的时候,没有对用户输入数据的合法性 ...
- 国际化(i18n)
一.国际化开发概述 软件的国际化:软件开发时,要使它能同时应对世界不同地区和国家的访问,并针对不同地区和国家的访问,提供相应的.符合来访者阅读习惯的页面或数据. 国际化(internationaliz ...
- jdbc中c3p0的配置信息
<c3p0-config> <!-- 这是默认配置信息 --> <default-config> <!-- 连接四大参数配置 --> <prope ...