如下内容是翻译的官网文档RedLock和分区部分,能够简单了解分布式锁在redis如何实现及其方式java
redis分区的方法node
##redis实现的分布式锁RedLock算法,分布式锁,即在多个master上获取同一个锁redis
1.in order to get the lock,the client get the current ms time算法
2.顺序对n个实例获取锁权限(n个都是master),尝试锁时,设置链接超时时间,防止因为实例挂了,致使长时间没法执行操做数据库
3.计算为了获取锁消耗的时间,有且仅有,client获取了超过半数个机器的锁,且获取锁消耗的时间小于锁的有效期,就被认为client获取了锁缓存
4.锁被获取后,其合法的持续时间为:初始设置的有效时间-为了获取锁消耗的时间异步
5.若是client因为某些缘由没有成功获取锁,它会解锁全部master实例(即便有的实例它不可能锁成功)分布式
###算法是异步的吗url
算法的前提是:多个进程或机器不会同步时钟,致使时间波动,没法计算出准确的获取锁消耗时间,或不一样的计算机,时间流逝的速度浮动范围很小.net
##redis分区:
###分区的优势
1.造成一个更大的数据库
2.计算能力加强,运用更多的核心数
基本的分区方式
1.范围分区,用一个路由表记录1-1000放哪一个实例,1001-2000放哪一个实例,缺点也很明显,须要路由表,key的类型不少的时候,须要给不一样类型的key作不一样的路由
2.hash分区,crc32(key),获取一个很大的数字,用这个数字和redis实例数取模,找到对应实例
3.一致性hash分区
###不一样的实现
1.client端分区:client直接选取正确的redis
2.代理辅助分区:client请求proxy,proxy forward正确的redis,并返回结果给client
3.查询路由;client随机发给一个redis,redis forward query to right node,也有redis查询路由后,返回正确的redis地址,客户端再去正确的redis取,可是这样会多请求一次redis
###分区的不足
1.不提供同时操做多个key
2.redis事务直接不可用
3.分区的粒度是key,若是一个key存了很大的数据量,分区也迫不得已
4.数据处理变得复杂,若是你想备份,须要聚合多个实例
5.扩容或缩容变得复杂,redis集群支持透明的重平衡数据,可是client分区,代理分区却不能透明的支持这个特性(预分区技术能解决)
存储数据?缓存?
若是redis做为数据存储,那么一个key老是须要对应到同一个redis
分布式锁 1.互斥 setNX 2.死锁 timeout 3.可重入 setNx(xx,xx,1) -> setNx(xx,xx,2) 4.订阅subscrible 频道,锁释放时publish消息,redis server和client会创建长链接,订阅时,java须要开发一个listener来处理消息,实现onMessage方法
https://www.jianshu.com/p/de5a69622e49
##redis为何快
redis快的缘由,基于内存,不会再操做时进行磁盘I/O,key,val采用dict,相似HashMap,时间复杂度为1,key多为string,没有hash冲突 单线程避免了无谓的cpu上下文切换,无锁 非阻塞IO,epoll多路复用 epoll 是只轮询那些真正发出了事件的流),而且只依次顺序的处理就绪的流,这种作法就避免了大量的无用操做,只有一个线程来处理这些I/O,key
确实没法利用多cpu的优点,可是通常状况下,cpu不是redis的瓶颈,可是能够用单机启用多个redis来弥补
减小耗时的命令,大对象,大对象还可能致使频繁查询打满带宽