• 分布式锁


    分布式锁-redis

    import org.slf4j.Logger;
    import org.slf4j.LoggerFactory;
    import org.springframework.beans.factory.annotation.Autowired;
    import org.springframework.data.redis.core.StringRedisTemplate;
    import org.springframework.stereotype.Component;
    import org.springframework.util.StringUtils;
    
    import java.util.concurrent.TimeUnit;
    
    /**
     *
     */
    @Component
    public class RedisLock {
     
        Logger logger = LoggerFactory.getLogger(this.getClass());
    
        @Autowired
        private StringRedisTemplate redisTemplate;
    
        /**
         * 加锁
         * @param key
         * @param currentTimeMillis 当前时间
         * @param timeoutMillis 超时时间
         * @return
         */
        public boolean lock(String key,long currentTimeMillis, long timeoutMillis) {
            String value=  String.valueOf(currentTimeMillis+timeoutMillis);
            //这个其实就是setnx命令,只不过在java这边稍有变化,返回的是boolea
            if (redisTemplate.opsForValue().setIfAbsent(key, value)) {
                //这个过期不是原子操作,只是正常为了设置
                redisTemplate.expire(key,timeoutMillis, TimeUnit.MILLISECONDS);
                return true;
            }
     
            //避免死锁,且只让一个线程拿到锁
            String currentValue = redisTemplate.opsForValue().get(key);
            //如果锁过期了
            if (!StringUtils.isEmpty(currentValue) && Long.parseLong(currentValue) < System.currentTimeMillis()) {
                //获取上一个锁的时间
                String oldValues = redisTemplate.opsForValue().getAndSet(key, value);
                /*
                   只会让一个线程拿到锁
                   如果旧的value和currentValue相等,只会有一个线程达成条件,因为第二个线程拿到的oldValue已经和currentValue不一样了
                 */
                if (!StringUtils.isEmpty(oldValues) && oldValues.equals(currentValue)) {
                    return true;
                }
            }
            return false;
        }
     
     
        /**
         * 解锁
         * @param key
    
         */
        public void unlock(String key, long currentTimeMillis, long timeoutMillis) {
            String value=  String.valueOf(currentTimeMillis+timeoutMillis);
            try {
                String currentValue = redisTemplate.opsForValue().get(key);
                if (!StringUtils.isEmpty(currentValue) && currentValue.equals(value)) {
                    redisTemplate.opsForValue().getOperations().delete(key);
                }
            } catch (Exception e) {
                logger.error("『redis分布式锁』解锁异常,{}", e);
            }
        }
    }

     使用

  • 相关阅读:
    【西瓜书】周志华《机器学习》学习笔记与习题探讨(一)
    01-线性回归算法
    NumPy 字符串函数
    Numpy函数分类
    Excel一对多查询(index+small+if)
    支付机构MRC模
    数据分析方法论
    窗口函数/解析函数
    数据分析
    底层逻辑
  • 原文地址:https://www.cnblogs.com/xiaomaoyvtou/p/14924058.html
Copyright © 2020-2023  润新知