java雪崩_【并发编程】java 如何解决redis缓存穿透、缓存雪崩(高性能示例代码)...

【并发编程】java 如何解决redis缓存穿透、缓存雪崩(高性能示例代码)

发布时间:2018-11-22 16:48,

浏览次数:872

, 标签:

java

redis

<>缓存穿透

* 1、什么是缓存穿透:

从字面上理解,缓存穿透就是运行程序击穿了你的Redis缓存服务器,去访问MySQL数据库;

由于Redis存在一定的命中概率,进来的请求发现Redis中并没有相关数据或者是没有命中指定数据,会去数据库查询。

* 2、缓存穿透有什么危害:

如果大量请求进来,直接去访问数据库服务查询,数据库服务器CPU短时间内会超负载运行,致使数据库服务宕机。

解决思路:

* 1、简单:加synchronized关键字(同步锁);

* 2、推荐:使用Lock对象的tryLock()方法(定时锁); package com.cn.seesun2012.cache; import java

.util.concurrent.TimeUnit; import java.util.concurrent.locks.Lock; import java.

util.concurrent.locks.ReentrantLock; import com.cn.seesun2012.mapper.

ProductInfoMapper; import com.cn.seesun2012.util.JedisClient; /** * *

┏┓  ┏┓+ + *        ┏┛┻━━━┛┻┓ + + *        ┃       ┃ *        ┃   ━   ┃ ++ + + +

*        ████━████ ┃+ *        ┃       ┃ + *        ┃   ┻   ┃ *

┃       ┃ + + *        ┗━┓   ┏━┛ *          ┃   ┃ *          ┃   ┃ + + +

+ *          ┃   ┃ God beast body, code no BUG *          ┃   ┃ + 神兽护体,代码无BUG *

┃   ┃ *          ┃   ┃  + *          ┃    ┗━━━┓ + + *          ┃

┣┓ *          ┃        ┏┛ *          ┗┓┓┏━┳┓┏┛ + + + + *

┃┫┫ ┃┫┫ *           ┗┻┛ ┗┻┛+ + + + * * @title: 商品信息-模块 * @version

v1.0.0 * @author csdn:seesun2012 * @date 2018年11月22日 下午17:21:33 周四 * */ public

class ProductInfoCache { // Jedis 缓存对象 private JedisClient jedisClient; //

商品信息XML映射类 private ProductInfoMapper productInfoMapper; // 缓存业务KEY前缀 private

static final String PRODUCT_KEY = "项目名.模块名.业务名."; // 锁-实例 private Lock lock =

new ReentrantLock(); /** * 获取商品图片路径 * @param id */ public synchronized String

getProductImgUrlById(String id){ // 获取缓存 String product = jedisClient.get(

PRODUCT_KEY+ id); if (null == product) { // 如果没有获取锁等待3秒,SECONDS代表:秒 try { if (

lock.tryLock(3, TimeUnit.SECONDS)) { try { // 获取锁后再查一次,查到了直接返回结果 product =

jedisClient.get(PRODUCT_KEY + id); if (null == product) { // 查询数据库 product =

productInfoMapper.getProductInfoById(id); if (null == product) { //

假设有10000人的并发量,第一次查也没有数据, // 那么设定为"null",加入有效期6秒 jedisClient.setex((PRODUCT_KEY+

id), "null", 6); return product; } jedisClient.set((PRODUCT_KEY + id), product);

return product; } return product; } catch (Exception e) { product = jedisClient.

get(PRODUCT_KEY + id); } finally { // 释放锁(成功、失败都必须释放,如果是lock.tryLock()方法会一直阻塞在这)

lock.unlock(); } } else { product = jedisClient.get(PRODUCT_KEY + id); } }

catch (InterruptedException e) { product = jedisClient.get(PRODUCT_KEY + id); }

} return product; } }

tryLock(long time, TimeUnit

unit)方法和tryLock()方法是类似的,只不过区别在于这个方法在拿不到锁时会等待一定的时间,在时间期限之内如果还拿不到锁,就返回false;如果一开始拿到锁或者在等待期间内拿到了锁,则返回true。

Lock的使用法方法:

https://blog.csdn.net/zengmingen/article/details/53259394?utm_source=blogxgwz7

<>缓存雪崩

* 1、什么是缓存雪崩: 缓存在同一时间内大量键过期(失效),接着来的一大波请求瞬间都落在了数据库中导致连接异常。

解决思路:

* 1、也是像解决缓存穿透一样加锁排队,实现同上;

* 2、建立备份缓存,缓存A和缓存B,A设置超时时间,B不设值超时时间,先从A读缓存,A没有读B,并且更新A缓存和B缓存;

<>布隆过滤器

。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。

。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。

。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。

。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。

。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。

。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。

<>持续更新中…

如有对思路不清晰或有更好的解决思路,欢迎与本人交流,QQ群:273557553,个人微信:seesun2012

你的提问是小编创作灵感的来源!

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值