分布式锁介绍

引言

分布式锁是一种用于协调不同进程或线程对共享资源的访问控制的机制。在分布式系统中,由于多个节点可能同时访问或修改同一资源,因此需要一个中心化的协调机制来确保资源的访问是有序的,避免数据不一致的问题。

分布式锁的特性:

互斥性

任意时刻,只有一个客户端能持有锁。

可重入性

同一个客户端可以多次获取同一把锁。

超时释放

持有锁的客户端在一定时间内没有主动释放锁,锁应该会被自动释放,防止死锁。

容错性

分布式锁服务要有容错机制,不会因为某个节点故障而导致锁失效。

实现方式

分布式锁有多种实现方式,以下列举了几种常见的实现方式及其在Java中的代码示例:

1. 基于Redis实现

利用Redis的setnx命令可以很容易地实现分布式锁。
2. 基于Zookeeper实现
利用Zookeeper的顺序临时节点和Watcher机制可以实现分布式锁。
import org.apache.zookeeper.CreateMode;
import org.apache.zookeeper.WatchedEvent;
import org.apache.zookeeper.Watcher;
import org.apache.zookeeper.ZooDefs;
import org.apache.zookeeper.ZooKeeper;
import org.apache.zookeeper.ZooDefs.Ids;

import java.util.concurrent.CountDownLatch;

public class ZookeeperDistributedLock implements Watcher {
private final ZooKeeper zk;
private final String lockPath;
private final CountDownLatch latch = new CountDownLatch(1);

public ZookeeperDistributedLock(ZooKeeper zk, String lockPath) {  
    this.zk = zk;  
    this.lockPath = lockPath;  
}  

public void acquire() throws Exception {  
    if (zk.exists(lockPath, false) != null) {  
        zk.exists(lockPath, true, this);  
        latch.await();  
    } else {  
        zk.create(lockPath, new byte[0], Ids.OPEN_ACL_UNSAFE, CreateMode.EPHEMERAL_SEQUENTIAL);  
    }  
}  

@Override  
public void process(WatchedEvent event) {  
    if (event.getPath().equals(lockPath) && event.getType() == WatchedEvent.EventType.NodeDeleted) {  
        latch.countDown();  
    }  
}  

public void release() throws Exception {  
    zk.delete(zk.getCurrentEphemeralNode(lockPath), -1);  
}  

}
使用示例:
以下是一个基于Redis实现的分布式锁的使用示例:
import redis.clients.jedis.Jedis;

public class DistributedLockExample {
public static void main(String[] args) {
// 初始化Redis连接
Jedis jedis = new Jedis(“localhost”, 6379);
复制代码
// 定义锁的名称和过期时间
String lockKey = “myLock”;
int expireTime = 10 * 1000; // 10秒

// 创建分布式锁对象  
RedisDistributedLock lock = new RedisDistributedLock(jedis, lockKey, expireTime);  
  
try {  
    // 尝试获取锁  
    if (lock.tryLock()) {  
        try {  
            // 成功获取锁,执行临界区代码  
            System.out.println("Acquired lock, executing critical section...");  
            // 模拟耗时操作  
            Thread.sleep(5000);  
        } finally {  
            // 释放锁  
            lock.unlock();  
        }  
    } else {  
        // 获取锁失败,处理获取锁失败的逻辑  
        System.out.println("Failed to acquire lock, doing something else...");  
    }  
} catch (Exception e) {  
    e.printStackTrace();  
} finally {  
    // 关闭Redis连接  
    if (jedis != null) {  
        jedis.close();  
    }  
}  

}

相关推荐

  1. 分布式介绍

    2024-04-15 05:28:04       41 阅读
  2. Zookeeper实现分布式(Zk分布式

    2024-04-15 05:28:04       38 阅读
  3. 【redis笔记】分布式

    2024-04-15 05:28:04       60 阅读

最近更新

  1. docker php8.1+nginx base 镜像 dockerfile 配置

    2024-04-15 05:28:04       94 阅读
  2. Could not load dynamic library ‘cudart64_100.dll‘

    2024-04-15 05:28:04       101 阅读
  3. 在Django里面运行非项目文件

    2024-04-15 05:28:04       82 阅读
  4. Python语言-面向对象

    2024-04-15 05:28:04       91 阅读

热门阅读

  1. MyBatis 中的动态 SQL 是什么? 如何使用动态 SQL?

    2024-04-15 05:28:04       43 阅读
  2. Linux网络服务器编程:TCP与UDP详解

    2024-04-15 05:28:04       37 阅读
  3. 如何进行JVM的调优

    2024-04-15 05:28:04       33 阅读
  4. macos、windows 思维导图 xmind pro

    2024-04-15 05:28:04       205 阅读
  5. xss攻击原理与解决方法

    2024-04-15 05:28:04       66 阅读
  6. Kotlin 面试题

    2024-04-15 05:28:04       49 阅读
  7. 责任链模式学习进阶--一起学习吧之数据库

    2024-04-15 05:28:04       45 阅读
  8. RS-232、RS-422及RS-485串行数据标准的选择及使用

    2024-04-15 05:28:04       45 阅读