1.什么是Redis
2.Redis的用途
Redis是一个开源的高性能键值存储系统,主要用于缓存、消息队列、分布式锁、计数器等场景。
-
缓存:Redis可以将常用的数据存储在内存中,以提高读取速度。它支持多种数据结构,如字符串、哈希、列表、集合和有序集合,可以灵活地存储和查询数据。
-
消息队列:Redis的发布订阅功能可以用作简单的消息队列,用于解耦和异步处理系统之间的通信。生产者将消息发布到特定的频道,而消费者则订阅感兴趣的频道,从中获取消息。
-
分布式锁:Redis的单线程特性使得其在实现分布式锁时非常方便。通过使用SETNX命令可以实现基于Redis的分布式锁,避免多个节点同时对同一资源进行访问。
-
计数器:Redis的INCR和INCRBY命令可以非常高效地实现计数器功能。可以用来记录用户访问次数、页面浏览量等。
此外,Redis还可以用于实现会话缓存、排行榜、实时数据分析等各种场景。 由于其快速、可靠和灵活的特性,Redis在各种应用场景中被广泛使用。
3.Redis 数据类型
1. 字符串(String):存储一个字符串值,常用于缓存数据、计数器、分布式锁等场景。
2. 哈希(Hash):存储键值对集合,适合存储对象信息,如用户信息、商品信息等。
3. 列表(List):按插入顺序存储字符串元素,可以实现队列、栈、消息队列等功能。
4. 集合(Set):无序且唯一的字符串集合,支持交集、并集、差集等操作,适合存储标签、好友列表等。
5. 有序集合(Sorted Set):在集合的基础上增加了一个权重属性,可以对元素进行排序,并且保证元素唯一性,常用于排行榜、社交网络等。
这些数据类型与对应的应用场景的实现关系如下:
- 字符串:适合存储单个键值对,常用于缓存和简单计数器。
- 哈希:适合存储对象信息,如用户信息、文章信息等。
- 列表:适合实现队列和栈,可以用于任务队列、消息队列等场景。
- 集合:适合存储唯一性、无序的元素,可以用于好友列表、标签管理等。
- 有序集合:适合存储需要排序的元素,如排行榜、时间线等。
需要根据具体的业务需求和数据特点来选择合适的数据类型和实现方式。
字符串类型:
散列表:
列表:
集合set:
有序集合ZSet:
事务:
缓存穿透
-
- 什么是缓存穿透?
缓存穿透是指客户端请求的数据在缓存中和数据库中都不存在,这样缓存永远不会生效,这些请求都会打到数据库。
- 什么是缓存穿透?
-
- 常见的两种解决方案
(1)缓存空对象
简单的来说,就是请求之后,发现数据不存在,就将null值打入Redis中。
优点:实现简单,维护方便
缺点:额外的内存消耗
可能造成短期的不一致
- 常见的两种解决方案
-
思路分析:
当我们客户端访问不存在的数据时,先请求 redis,但是此时 redis 中没有数据,
此时会访问到数据库,但是数据库中也没有数据,这个数据穿透了缓存,直击数据库,
我们都知道数据库能够承载的并发不如 redis 这么高,如果大量的请求同时过来访问这种不存在的数据,这些请求就都会访问到数据库,简单的解决方案就是哪怕这个数据在数据库中也不存在,我们也把这个数据存入到 redis 中去,这样,下次用户过来访问这个不存在的数据,那么在 redis 中也能找到这个数据就不会进入到数据库了。
(2)布隆过滤
在客户端与Redis之间加了一个布隆过滤器,对请求进行过滤。
布隆过滤器是一种用于快速判断一个元素是否存在于给定集合中的概率型数据结构。它基于哈希函数和位数组实现,具有高效的插入和查询操作。
- 布隆过滤器的原理如下:
- 初始化:创建一个位数组,长度为m,并将所有位都初始化为0。
- 插入操作:对于要插入的元素,使用k个不同的哈希函数将其映射到位数组上的k个位置,并将这些位置的值设为1。
- 查询操作:对于要查询的元素,同样使用k个哈希函数得到k个位置,如果这些位置上的值都为1,则判断元素存在于集合中;如果有任意一个位置上的值为0,则判断元素不存在于集合中。
- 布隆过滤器的局限性包括:
- 误判率:由于位数组中的某些位置可能被多个元素映射到,因此存在一定的误判率。在查询操作中,有可能出现将不存在的元素判断为存在的情况,但不会出现将存在的元素判断为不存在的情况。
- 内存占用:作为一种概率型数据结构,布隆过滤器需要使用较大的位数组来存储映射结果,因此占用较多的内存空间。
- 不支持删除操作:由于布隆过滤器的特殊结构,无法直接删除已插入的元素。若要实现删除操作,需要使用其他方法或结合其他数据结构。
优点:内存占用较少,没有多余 key
缺点:实现复杂 存在误判可能
综上所述
我们可以两种方案一起用,这样子最为保险。据统计使用布隆过滤器一般可以避免90%的无效请求。