Redis优雅地解决大Key读取(redis读取大key)
压力
高并发场景下,读取大Key的压力是一种普遍的问题,Redis常用于缓存相关服务,并且对大Key读取做了优化。对于大Key读取,能够优雅地处理这种现象。
##### 1.切分大Key
在Redis读取大Key的场景下,首先要做的就是切分大Key,并将之分到多个小Key下。切分的时候需要考虑用户的完整使用体验,将界面上不容易区分的部分切分,但是又不影响整体的流程。切分后的小Key,可以精准的跟踪用户行为,可以更直观的分析数据,而且读取数据的时候也更快更灵活,如下所示:
//例如:将大Key"userInfo"切分为以下几个小Key
userInfo:usernameuserInfo:phone
userInfo:eml
##### 2.哈希类型存储
对大Key读取的时候,我们可以使用哈希类型来存储,相比于字符串或者列表,哈希类型只要取出一次,就能读取出多个字段,大大减少IO操作次数,提高性能。如下所示:
//在存储的时候:
HSET userinfo username TomHSET userinfo phone 15511111111
HSET userinfo eml example@163.com
//在获取的时候:HMSET userinfo username Tom phone 15511111111 eml example@163.com
+ HMGet命令可以快速获取用户手机号,邮箱等字段值,而不需要遍历全部字段,大幅减少IO操作。
+ 由于大量Key使用哈希类型存储,碎片化问题会急剧加剧,而因此Redis 4.0之后的版本采用了虚拟槽(cluster slot)的技术,将哈希类型的存储分散到多个节点中,使Redis在存储哈希类型的时候更加稳定。
##### 3.对象缓存
在存储大Key的时候,可以使用JSON格式存储,然后将其缓存到Redis中,极大的简化了存储和读取的工作量。实现方式如下所示:
//定义User对象
class User{ private String username;
private String phone; private String eml;
//getter/setter}
//存储对象 JSONObject userJsonObject = new JSONObject();
//将user对象转换成jsonuserJsonObject.put("username",user.getUsername());
userJsonObject.put("phone",user.getPhone());userJsonObject.put("eml",user.getEml());
//存储到Redisjedis.set("userInfo",userJsonObject.toJSONString());
//读取对象String userJsonString = jedis.get("userInfo");
//将json转换成User对象User user = (User)JSONObject.toBean(JSONObject.fromObject(userJsonString),User.class);
使用对象缓存能够更简单的让我们的数据存储在Redis中,同时读取也更加方便。
以上三个方式,都可以优雅的解决大Key读取的压力,能有效的提高系统的并发吞吐性能。