package redis;

import redis.clients.jedis.Jedis;
import redis.clients.jedis.JedisPool; public class RedisLock { public static void main(String[] args) { JedisPool jedisPool = new JedisPool("127.0.0.1", 6379);
// 从连接池中获取一个jedis对象
Jedis jedis = jedisPool.getResource(); //简单加redis分布式锁的方式
boolean lock = false;
String key = "mylock";
String value = System.currentTimeMillis()+""; try {
//50秒自动解锁
String setResult = jedis.set(key,value , "nx", "ex", 50L);
long startTime = 0;
if (setResult!=null) {
lock = true;
startTime = System.currentTimeMillis();
} //没有获取到锁,退出
if (!lock) {
return;
} //执行到了这一步说明已经获取到锁
// doSth long endTime = System.currentTimeMillis();
//如果超时解锁
if ((endTime-startTime)>5000) {
//打印日志
System.out.println("出现超时解锁-----------key:"+key);
} } catch (Exception e) {
e.printStackTrace();
}finally {
//这里是为了避免超时后,释放掉其他线程的同名锁
//但是有个问题,就是下面的代码不是原子操作,可能会有问题,这里忽略
String s = jedis.get(key);
if (value.equals(s)) {
//释放锁
jedis.del(key);
}
} }
}
package redis;

import java.util.HashMap;
import java.util.Map; import redis.clients.jedis.Jedis;
import redis.clients.jedis.JedisPool; public class RedisReentrantLock { private ThreadLocal<Map<String,Integer>> lockers = new ThreadLocal<>();
private Jedis jedis; public RedisReentrantLock(Jedis jedis) {
super();
this.jedis = jedis;
} private boolean _lock(String key) {
return jedis.set(key,"" , "nx", "ex", 5L)!=null;
} private void _unlock(String key) {
jedis.del(key);
} private Map<String, Integer> currentLockers(){
Map<String, Integer> refs = lockers.get();
if (refs !=null) {
return refs;
}
lockers.set(new HashMap<String, Integer>());
return lockers.get();
} public boolean lock(String key) {
Map<String, Integer> refs = currentLockers();
Integer refCnt = refs.get(key);
if (refCnt!=null) {
refs.put(key, refCnt+1);
return true;
}
boolean ok = this._lock(key);
if (!ok) {
return false;
} refs.put(key, 1);
return true;
} public boolean unlock(String key) {
Map<String, Integer> refs = currentLockers();
Integer refCnt = refs.get(key);
if (refCnt == null) {
return false;
}
refCnt -= 1;
if (refCnt>0) {
refs.put(key, refCnt);
}else {
refs.remove(key);
this._unlock(key);
}
return true;
} public static void main(String[] args) {
JedisPool jedisPool = new JedisPool("127.0.0.1", 6379);
// 从连接池中获取一个jedis对象
Jedis jedis = jedisPool.getResource();
RedisReentrantLock redisLock = new RedisReentrantLock(jedis);
System.out.println(redisLock.lock("lock1"));
System.out.println(redisLock.lock("lock1"));
System.out.println(redisLock.unlock("lock1"));
System.out.println(redisLock.unlock("lock1"));
} }

redis分布式锁练习【我】的更多相关文章

  1. 利用redis分布式锁的功能来实现定时器的分布式

    文章来源于我的 iteye blog http://ak478288.iteye.com/blog/1898190 以前为部门内部开发过一个定时器程序,这个定时器很简单,就是配置quartz,来实现定 ...

  2. Redis分布式锁

    Redis分布式锁 分布式锁是许多环境中非常有用的原语,其中不同的进程必须以相互排斥的方式与共享资源一起运行. 有许多图书馆和博客文章描述了如何使用Redis实现DLM(分布式锁管理器),但是每个库都 ...

  3. redis分布式锁和消息队列

    最近博主在看redis的时候发现了两种redis使用方式,与之前redis作为缓存不同,利用的是redis可设置key的有效时间和redis的BRPOP命令. 分布式锁 由于目前一些编程语言,如PHP ...

  4. redis咋么实现分布式锁,redis分布式锁的实现方式,redis做分布式锁 积极正义的少年

    前言 分布式锁一般有三种实现方式:1. 数据库乐观锁:2. 基于Redis的分布式锁:3. 基于ZooKeeper的分布式锁.本篇博客将介绍第二种方式,基于Redis实现分布式锁.虽然网上已经有各种介 ...

  5. spring boot redis分布式锁

    随着现在分布式架构越来越盛行,在很多场景下需要使用到分布式锁.分布式锁的实现有很多种,比如基于数据库. zookeeper 等,本文主要介绍使用 Redis 做分布式锁的方式,并封装成spring b ...

  6. Redis分布式锁的正确实现方式

    前言 分布式锁一般有三种实现方式:1. 数据库乐观锁:2. 基于Redis的分布式锁:3. 基于ZooKeeper的分布式锁.本篇博客将介绍第二种方式,基于Redis实现分布式锁.虽然网上已经有各种介 ...

  7. Redis分布式锁---完美实现

    这几天在做项目缓存时候,因为是分布式的所以需要加锁,就用到了Redis锁,正好从网上发现两篇非常棒的文章,来和大家分享一下. 第一篇是简单完美的实现,第二篇是用到的Redisson. Redis分布式 ...

  8. redis分布式锁实践

    分布式锁在多实例部署,分布式系统中经常会使用到,这是因为基于jvm的锁无法满足多实例中锁的需求,本篇将讲下redis如何通过Lua脚本实现分布式锁,不同于网上的redission,完全是手动实现的 我 ...

  9. Redis分布式锁的try-with-resources实现

    Redis分布式锁的try-with-resources实现 一.简介 在当今这个时代,单体应用(standalone)已经很少了,java提供的synchronized已经不能满足需求,大家自然 而 ...

  10. 关于分布式锁原理的一些学习与思考-redis分布式锁,zookeeper分布式锁

    首先分布式锁和我们平常讲到的锁原理基本一样,目的就是确保,在多个线程并发时,只有一个线程在同一刻操作这个业务或者说方法.变量. 在一个进程中,也就是一个jvm 或者说应用中,我们很容易去处理控制,在j ...

随机推荐

  1. toolbox 中创建nginx服务器,使用localhost不能访问

    使用toolbox 工具使用docker创建nginx 容器,使用localhost不能访问? 使用docker run --rm -d --name dweb  -p 80:80 nginx 命令执 ...

  2. notify()和 notifyAll()有什么区别?(未完成)

    notify()和 notifyAll()有什么区别?(未完成)

  3. MATLAB中.m文件生成.dll

    1.配置编译环境 在命令行窗口输入: mbuild -setup 如果出现以下提示信息说明成功: 如果提示信息为: 错误使用mbuild(line 164) Unable to complete su ...

  4. mysql:用户自定义变量关联失效

    自定义变量的属性和限制 使用自定义变量的查询,无法使用查询缓存. 不能在使用常量或者标识列的地方使用自定义变量,例如表名.列明和LIMIT子句中. 用户自定义变量的生命周期是在一个连接中有效,所以不能 ...

  5. //点击按钮加减音频音量到最小会出现bug什么意思???

    <!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8&quo ...

  6. 015_linux驱动之_signal

    1. 首先看应用程序 1. 首先分析第二点使用函数signal(SIGIO, my_signal_fun);来设置,当驱动程序传递信号给应用程序时候会调用第一点的程序 2. 第三点是设置相关参数 (二 ...

  7. 可以粘贴Word文档中图片的编辑器

    Chrome+IE默认支持粘贴剪切板中的图片,但是我要发布的文章存在word里面,图片多达数十张,我总不能一张一张复制吧?Chrome高版本提供了可以将单张图片转换在BASE64字符串的功能.但是无法 ...

  8. bzoj 5072

    对于某一大小的连通子图包含的黑点的数目的最大值和最小值都能取到考虑树形dp$f[i][j]$ 表示从 $i$ 的子树中选出大小为 $j$ 的联通子图黑点数目的最小值$g[i][j]$ 表示从 $i$ ...

  9. python+opencv 图像预处理

    一 python 生成随机字符串序列+ 写入到图片上 from PIL import Image,ImageDraw,ImageFont import numpy as np import rando ...

  10. codeforces1213F tarjan缩点+拓扑排序

    题意 给定两个长度为n的排列p和q,构造一个字符串s满足\(s[p_i]<=s[p_{i+1}]\)和\(s[q_i]<=s[q_{i+1}]\),且满足字符串中不同字符的个数不少于k. ...