java实现分布式锁01

java实现分布式锁

package com.yiran.redis;

import org.junit.Test;
import redis.clients.jedis.Jedis;

import java.net.PortUnreachableException;

/**
 * @program: BigdataSrc
 * @description:
 * @author: Mr.Yang
 * @create: 2021-05-15 14:41
 **/

public class RdisTest1 {
    public static Jedis conn = new Jedis("hadoop102", 6379);

    /**
     * 分布式锁的设计:
     * 全局进程可访问
     * 具有唯一性,拿到所的进程or线程执行任务,其他阻塞
     * 集群异常处理
     * 防止死锁):
     *  集群在释放锁之前挂了
     * 数据丢失):
     *  客户端在数据拿到锁后,redis服务挂掉
     * 解决方案:
     *  使用setnx争抢锁
     *  使用expire设置过期时间
     * 问题:
     *  setnx 之后 expire之前服务挂了
     *  使用set nx ex实现一致性操作
     */
    @Test
    public void dbs_lock1(){

        Long count=100L;
        conn.set("java_count","100");
        while(true) {
            // 实现分布式锁 set k v nx ex time
            String lock = conn.set("java_lock", String.valueOf(1), "nx", "ex", 1000);
            System.out.println(lock + "hello");
            if ("OK".equals(lock) && count>=1) {
                count = conn.decr("java_count");
                System.out.println(count);
                conn.del("java_lock");
            }else {
                break;
            }
        }
    }

    /**
     * 实现互斥锁
     */
    @Test
    public void dbs_lock2(){
        Long count=100L;
        conn.set("java_count","100");
        String threadName = Thread.currentThread().getName();
        while(true) {
            // 实现分布式锁 set k v nx ex time
            // 实现唯一id
            String lock = conn.set("java_lock", threadName, "nx", "ex", 1000);
            System.out.println(lock + "hello");
            if ("OK".equals(lock) && count>=1) {
                count = conn.decr("java_count");
                System.out.println(count);
                // 实现唯一id判断
                if (threadName.equals(conn.get("java_lock"))) {
                    conn.del("java_lock");
                }
            }else {
                break;
            }
        }
    }

    /**
     * 实现可重入锁
     * 保证当前线程可重复提交
     * synchornized就是可重入锁:底层做了判断,放行连续拿到锁的情况
     */
    @Test
    public void dbs_lock3(){
        Long count=100L;
        conn.set("java_count","100");
        String threadName = Thread.currentThread().getName();
        while(true) {
            // 实现分布式锁 set k v nx ex time
            // 实现唯一id
            String lock = conn.set("java_lock", threadName, "nx", "ex", 1000);
            System.out.println(lock + "hello");
            // 此处逻辑修改 实现可重入锁
            if (("OK".equals(lock) || threadName.equals(conn.get("java_lock"))) && count>=1) {
                count = conn.decr("java_count");
                System.out.println(count);
                // 实现唯一id判断
                if (threadName.equals(conn.get("java_lock"))) {
                    conn.del("java_lock");
                }
            }else {
                break;
            }
        }
    }
}

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值