redis和zk实现分布式锁有什么区别_redis分布式锁和zk分布式锁区别

redis和zk实现分布式锁有什么区别_redis分布式锁和zk分布式锁区别前言本文介绍下分布式锁的一个使用场景分享本文的缘由是因为今天在写代码时需要处理一个原子性问题,场景是:业务功能需要先查询数据,再根据数据判断是否要更新数据,在这个查询+更新的过程必然会存在高并发下的原子性问题那么如何解决这个问题呢,那么就要说到我们的主角:分布式锁了分布式锁介绍分布式锁:即在多集群多节点环境下确保只有一个线程可以拿到锁,防止并发出现的问题,类似于synchronized,只不过synchronized不能处理多节点的问题解决上述问题的一种解决方式就是使用分布式锁,虽然性能会比较低

大家好,又见面了,我是你们的朋友全栈君。如果您正在找激活码,请点击查看最新教程,关注关注公众号 “全栈程序员社区” 获取激活教程,可能之前旧版本教程已经失效.最新Idea2022.1教程亲测有效,一键激活。

Jetbrains全系列IDE使用 1年只要46元 售后保障 童叟无欺

前言

本文介绍下分布式锁的一个使用场景
分享本文的缘由是因为今天在写代码时需要处理一个原子性问题,场景是:业务功能需要先查询数据,再根据数据判断是否要更新数据,在这个查询+更新的过程必然会存在高并发下的原子性问题

那么如何解决这个问题呢,那么就要说到我们的主角:分布式锁了

分布式锁介绍

分布式锁:即在多集群多节点环境下确保只有一个线程可以拿到锁,防止并发出现的问题,类似于synchronized,只不过synchronized不能处理多节点的问题

解决上述问题的一种解决方式就是使用分布式锁,虽然性能会比较低,但是笔者的场景是一个统计功能,并且是异步的,所以并不影响性能
核心代码如下:

场景介绍

try { 
   
	// 这里可以根据业务场景做分段锁,可以适当提升性能
	String lock = "lock_key";
	long keyValue = System.currentTimeMillis();
	// 获取锁,超时时间60秒每隔0.5秒尝试获取一次,60秒后没获取到则放弃
	boolean getLock = redisUtils.getLockByInterval(lock,keyValue,60,0.5,0);
	if(getLock) { 
   
		xxx
	}
} catch (Exception e) { 
   
  log.error("异常:", e);
} finally { 
   
    if(getLock) { 
   
        redisUtils.unLock(lock,keyValue);
    }
}

RedisUtils类getLockByInterval

  /** * 获取锁,如果没获取到那么每隔interval秒重试一次,重试直到timeout秒 * @param key * @param value * @param timeout 超时时间(单位秒) * @param interval 超时时间(单位秒) * @param currentTime 当前时间,调用时传0,只用于递归时间 * @return */
    public boolean getLockByInterval(String key,Object value,int timeout,double interval,double currentTime) { 
   
        if(currentTime > timeout) { 
   
            return false;
        }
        // 相当于redis的setnx命令
        boolean getLock = redisTemplate.opsForValue().setIfAbsent(key,value,timeout, TimeUnit.SECONDS);
        if(!getLock) { 
   
            //没有拿到锁就间隔interval再次尝试获取锁,直到总时间大于timeout
            try { 
   
                Thread.sleep(Double.valueOf(interval*1000).longValue());
            } catch (InterruptedException e) { 
   
                log.error("RedisUtils getLockByInterval error:",e);
            }
            currentTime += interval;
            // 递归
            return getLockByInterval(key,value,timeout,interval,currentTime);
        }
        return true;
    }

上述代码其实还是不够完美,当并发量足够大时可能存在某线程在超时时间内还是没有抢占到锁,因为获取锁的机制是按照间隔时间来获取的,并且属于非公平锁,即不是先到的线程有权利优先获取锁,这里可以看到redis的分布式锁并不是很友好,这里再介绍下zookeeper的分布式锁

分布式锁对比

redis分布式锁:通过redis通过的sexNx命令实现,即当key不存在时调用setNx返回true,否则返回false,获取不到锁的线程只能轮询去尝试获取锁
优点:性能高,使用简单,在允许偶发锁失效的场景下推荐使用
缺点:通过轮询抢占锁的机制不是很可靠,当某线程占用锁时间较长时可能导致其他线程抢占锁失败

zookeeper分布式锁:zk的分布式锁机制是利用zk的临时有序节点,即多个线程同时抢占锁会创建多个节点如a1->a2->a3->a4->a5…,只有拿到第一个节点的线程获得锁,里面节点注册是的watch机制,即a1使用完后会释放当前节点,同时watch下一个节点a2,依次类推
优点:不依靠轮询抢占锁,依靠的是节点间的通信,比较可靠,当业务场景要求比较高是推荐使用
缺点:性能不如redis缓存锁高

版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请联系我们举报,一经查实,本站将立刻删除。

发布者:全栈程序员-站长,转载请注明出处:https://javaforall.net/196177.html原文链接:https://javaforall.net

(0)
全栈程序员-站长的头像全栈程序员-站长


相关推荐

  • 生物标志物_简述生物标志物及其分类

    生物标志物_简述生物标志物及其分类NatureReviewCancer——最有前景的Biomarkers什么是生物标志物?生物标志物(Biomarkers)是指可以标记系统、器官、组织、细胞及亚细胞结构或功能变化以及可能发生变

    2022年8月2日
    11
  • 解决MyQL数据库中1045错误的方法——Windows系统「建议收藏」

    解决MyQL数据库中1045错误的方法——Windows系统「建议收藏」在各种各样的适用场所,MySQL会出现各种各样的问题,经过足足半年的长跑,我的数据库终于修复了Bug,可以重新使用了。数据库出问题,那可能是家常便饭了。经过这足足半年的煎熬,我决定在以后的日子里,记录下我在使用数据库时遇到的色彩缤纷的问题,以及这些问题的解决方法。由此,今天写了这篇博客。首先,给大家看看,这个问题是什么样子的。我在这里用到的MySQL可视化工具为Navicat。这个错误…

    2022年6月13日
    25
  • 关于ActionContext.getContext()的使用方法心得

    关于ActionContext.getContext()的使用方法心得

    2021年12月6日
    41
  • 偷偷地告诉学弟学妹们一个高效学习编程的秘密!大学四年悄悄惊艳他们,嘘

    偷偷地告诉学弟学妹们一个高效学习编程的秘密!大学四年悄悄惊艳他们,嘘今天来给大家谈一谈如何高效地学习编程。无论什么时候,找到学习的目标,以及学习的套路都非常的重要。找不到的话,就只能事倍功半,付出了很多努力,却迟迟得不到最好的回报。三四年前,我特别喜欢收藏文章,觉得有些技术文写得真好,忍不住收藏了!等过了一段时间后,闲得无聊,就去翻收藏夹,想着学一波,谁知道竟然找不到——不是微信给我删了,而是收藏夹里躺的“尸体”实在是太多了,根本就找不到。后来,我就总结了一个小窍门——每周收藏夹里最多躺五篇文章,如果想进来第六篇,之前的必须得清一篇。别小看这个小窍门,它真的有督促我去

    2022年9月27日
    0
  • SDN、NFV学习与理解「建议收藏」

    SDN、NFV学习与理解「建议收藏」这里写自定义目录标题欢迎使用Markdown编辑器新的改变功能快捷键合理的创建标题,有助于目录的生成如何改变文本的样式插入链接与图片如何插入一段漂亮的代码片生成一个适合你的列表创建一个表格设定内容居中、居左、居右SmartyPants创建一个自定义列表如何创建一个注脚注释也是必不可少的KaTeX数学公式新的甘特图功能,丰富你的文章UML图表FLowchart流程图导出与导入导出导入欢迎使用Ma…

    2022年9月9日
    0
  • Computer Science 学习第四章–CPU 指令集和指令处理

    Computer Science 学习第四章–CPU 指令集和指令处理

    2022年1月9日
    48

发表回复

您的邮箱地址不会被公开。 必填项已用 * 标注

关注全栈程序员社区公众号