zoukankan      html  css  js  c++  java
  • 分布式锁

    数据库分布式锁

    Redis实现分布式锁

    ZooKeeper实现分布式锁

    =======》

    1.「锁的互斥性」:在分布式集群应用中,共享资源的锁在同一时间只能被一个对象获取。

    2. 「可重入」:为了避免死锁,这把锁是可以重入的,并且可以设置超时。

    3. 「高效的加锁和解锁」:能够高效的加锁和解锁,获取锁和释放锁的性能也好。

    4. 「阻塞、公平」:可以根据业务的需要,考虑是使用阻塞、还是非阻塞,公平还是非公平的锁。

    数据库分布式锁

    在数据库的分布式锁的实现中,分为「悲观锁和乐观锁」「悲观锁的实现依赖于数据库自身的锁机制实现」

    --》悲观锁

    当一个数据库表被加上了排它锁,其它的客户端是不能够再对加锁的数据行加任何的锁,只能等待当前持有锁的释放锁。

    排它锁是基于InnoDB存储引擎的,在执行操作的时候,在sql中加入for update,可以给数据行加上排它锁。

    在代码的层面上使用connection.commit();,便可以释放锁,但是数据库复杂的加锁和解锁、事务等一系列消耗性能的操作,终归是无法抗高并发。

    --》乐观锁

    数据库乐观锁的方式实现分布式锁是基于「版本号控制」的方式实现,类似于「CAS的思想」,它认为操作的过程并不会存在并发的情况,只有在update version的时候才会去比较。

    Redis实现的分布式锁:

    Redis实现分布式锁的 方式,可以使用setnx、getset、expire、del这四个命令来实现。

    1. setnx:命令表示如果key不存在,就会执行set命令,若是key已经存在,不会执行任何操作。
    2. getset:将key设置为给定的value值,并返回原来的旧value值,若是key不存在就会返回返回nil 。
    3. expire:设置key生存时间,当当前时间超出了给定的时间,就会自动删除key。
    4. del:删除key,它可以删除多个key,语法如下:DEL key [key …],若是key不存在直接忽略。

    ZK实现的分布式锁:

    ZK实现的分布式锁的原理是基于一个「临时顺序节点」实现的,开始的时候,首先会在ZK中创建一个ParentLock持久化节点。

     当有client1请求锁的时候,,就会在ParentLock下创建一个临时顺序节点

     当client1创建完临时顺序节点后,就会检查ParentLock下面的所有的子节点,会判断自己前面是否还有节点,此时明显是没有的,所以获取锁成功

    当第二个客户端client2进来获取锁的时候,也会执行相同的逻辑,会先在创建一个临时的顺序节点,并且序号是排在第一个节点的后面

     并且第二步也会判断ParnetLock下面的所有的子节点,看自己是否是第一个,明显不是,此时就会加锁失败。

    那么此时client2会创建一个对client1的lock1的监听(Watcher),用于监听lock1是否存在,同时client2会进入等待状态

     当client1执行完自己的业务逻辑之后,就会删除锁,删除锁很简单,就是把这个lock1给删除掉

     此时就会通知client2:监听的lock1已经被删除,锁被释放,此时client2创建的lock2也就变成了第一个节点,尝试获取所得时候就会获取锁成功。

  • 相关阅读:
    [BZOJ4444][SCOI2015]国旗计划(倍增)
    [BZOJ4423][AMPPZ2013]Bytehattan(对偶图+并查集)
    [BZOJ4416][SHOI2013]阶乘字符串(子集DP)
    [BZOJ3203][SDOI2013]保护出题人(凸包+三分)
    [BZOJ4026]dC Loves Number Theory(线段树)
    51nod部分容斥题解
    [CodeVS4438]YJQ Runs Upstairs
    [HDU4906]Our happy ending
    牛客网NOIP赛前集训营-提高组(第四场)游记
    [BJWC2011]元素
  • 原文地址:https://www.cnblogs.com/KL2016/p/14605126.html
Copyright © 2011-2022 走看看