通俗易懂的Redis

通俗易懂的Redis
一,为什么要使用redis?

1.提高性能,缓存查询速度要比数据库查询速度快(内存VS硬盘)
2.提高并发能力,缓存分担了部分请求,支持更高的并发请求

问题:如果我们的缓存挂掉了,所有的请求全部都跑去数据库了,怎么办?

二,造成雪崩的原因?

1.redis挂掉了,所有的请求全部走了数据库
2.对缓存设置了相同的过期时间,导致了一段时间内缓存全部失效,所有请求全部走了数据库

问题:那么如何解决雪崩呢?

三,怎么去解决雪崩?

1.如果是设置了相同的过期时间而导致的雪崩,只需要给在缓存的时候给过期时间加一个随机值,这样就大幅度的避免了缓存在同一时间失效
2.如果是redis挂掉,那就要分3种情况了
		事发前----实现redis的高可用,使用主从架构+哨兵
		事发时----如果redis真的挂掉了,我们可以设置本地缓存(ehcache)+限流(hystrix),尽量避免我们的数据库被干死
		事发后----redis持久化,重启后自动从磁盘上加载数据,快速恢复缓存数据

四,缓存击穿

1.什么是缓存击穿?
	缓存击穿就是查询一个一定不存在的数据,缓存大量不命中,每次都去请求了数据库,进而失去了缓存的意义。
	(例如:一张表ID为1-100,我每次都用-1去查询,你能咋滴)
2.怎么解决缓存击穿?
   第一种:由于请求的参数不合法,我们可以使用布隆过滤器(BloomFilter)或者压缩filter提前拦截,不合法就不让这个请求到数据库层。
   第二种:当我们在数据库找不到这个数据得时候,我们可以将这个空对象设置到缓存里边去,下次请求的时候,我们可以从缓存里取(注意:空对象一般设置的过期时间比较短)

五,缓存与数据库双写一致

	读操作:
		固定套路一般都是,先判断缓存有没有,如果没有,去访问数据库拿到数据存进redis,返回给请求;如果redis有,那就直接返回给请求
		读的话,这样是没有问题的,但如果是写的操作呢?
		
	写操作:
		第一种情况:先更新了数据库,再删除缓存。(缓存刚好失效,线程a查询数据库,拿到了旧值,线程b把新值写进了数据库,然后线程b删除了缓存,线程a拿到的旧值放进了缓存),这种概率很低很低。
		解决方案:将需要删除的key放入队列中,自己消费消息,获取需要删除的key,不断的重试删除操						   作,直到成功

		第二种情况:先删除了缓存,再更新数据库。(线程a删除了缓存,线程b去查询,发现不存了,去数据库取旧值,旧值写进缓存,线程a将新值写入数据库)
		解决方案:将删除缓存,修改数据库,更新缓存等操作放到队列,实现串行化,保证每一步的动作都是先进先出

猜你喜欢

转载自blog.csdn.net/qq_40094875/article/details/86492833