Redis中你可能不知道的两个类

本人花费半年的时间总结的《Java面试指南》已拿腾讯等大厂offer,已开源在github ,欢迎star!

本文GitHub https://github.com/OUYANGSIHAI/JavaInterview 已收录,这是我花了6个月总结的一线大厂Java面试总结,本人已拿大厂offer,欢迎star

原文链接:blog.ouyangsihai.cn >> Redis中你可能不知道的两个类

阅读本文大概需要7分钟。

今天在项目中看到了这两个类,至于这两个类是做什么的,相信大家做开发的应该不难猜到,其实就是通过这两个类来操作Redis,不知道大家有没有用过这两个类,其实老实说我之前真的没用过,倒是在用的过程中确实出现了很多问题,今天就跟大家聊聊这两个类。

想必大家已经非常清楚,我们在项目中使用Redis肯定要通过一些类去操作从而设置或者获取一个值,操作的这个类可能是你们公司自己封装的工具类,但是也有公司没有封装工具类,是使用一些框架本身的一些类去进行操作的,更多的可能是Jedis,RedisTemplate和StringRedisTemplate这两个类可能使用的朋友比较少,也可能大家在使用了,只是我没用而已,但是不管怎么样,我们的目的都是一样的。

首先我们先来看下这两个类有什么关系,我们来看下源码

RedisTemplate类

Redis中你可能不知道的两个类

StringRedisTemplate类

Redis中你可能不知道的两个类

我们可以通过代码看出,StringRedisTemplate这个类是继承自RedisTemplate这个类的,虽然是这样的,但是我刚开始使用RedisTemplate往Redis中存储数据,使用StringRedisTemplate取出存储的数据时候,却是取不出来的,我就一直很纳闷,为什么会出现这样的情况,于是我连了下客户端,却发现,我存储的数据不是以可读的方式显示的。

这个是我们的代码


@GetMapping("getName")
    public void test() {

        // 使用 RedisTemplate 存储数据
        redisTemplate.opsForValue().set("name","张三");

        // 使用 StringRedisTemplate 获取数据
        String name = stringRedisTemplate.opsForValue().get("name");

        System.out.println("name : " + name);
    }

这是我们的结果

Redis中你可能不知道的两个类

我刚开始有点疑惑,为什么会拿不到数据呢?结果我用RedisClient客户端直接获取我存储的值,结果还是没有拿到值。

Redis中你可能不知道的两个类

这个时候就比较奇怪了,难道我的值没存储进去,那我使用RedisTemplate再获取一下,看能不能拿到。


@GetMapping("getName")
    public void test() {

        // 使用 RedisTemplate 存储数据
        redisTemplate.opsForValue().set("name","张三");

        // 使用 StringRedisTemplate 获取数据
        // String name = stringRedisTemplate.opsForValue().get("name");

        // 使用 RedisTemplate 获取数据
        String name = (String) redisTemplate.opsForValue().get("name");

        System.out.println("name : " + name);
    }

可以看到,我们拿到了我们设想的结果值

Redis中你可能不知道的两个类

如果结果值可以拿到,那是不是可以说明这个值已经成功保存在Redis中了,但是我们通过StringRedisTemplate却无法获取到,我们直接在客户端通过key去获取也获取不到,那这到底是为什么呢?

我们再来看看这两个类的源码,是不是还有一些我们没发现的密码。

RedisTemplate类

Redis中你可能不知道的两个类

StringRedisTemplate类

Redis中你可能不知道的两个类

通过查看源码我们确实发现了问题,原来这两个类具有不同的序列化方式

RedisTemplate使用的是 :

**        JdkSerializationRedisSerializer**

StringRedisTemplate使用的是 :

**        StringRedisSerializer**

原来是序列化捣的鬼,我们猜想是不是我们在存储键值对的时候RedisTemplate把我们的值转换为了其他的格式,怎么查看呢?我们通过客户端来查看一下,有没有name这个key。

Redis中你可能不知道的两个类

通过查看我们发现,根本没有name这个key,但是我们却发现存在一个不可读的key和value,是不是我们在存储的时候RedisTemplate已经帮助我们进行序列化为这种数据格式之后再存储到Redis中,其实确实是这样的,当你去通过RedisTemplate取值的时候,他会先把你的key序列化为它的数据格式,然后再去Redis中进行获取,将获取到的值再进行解析,就可以拿到我们想要的值。

既然清楚了RedisTemplate会把我们的数据序列化为我们不可读的格式,那么StringRedisTemplate又是怎么样的呢?我们再来看一看。


@GetMapping("getAge")
    public void test1() {

        // 使用 RedisTemplate 存储数据
        stringRedisTemplate.opsForValue().set("age","20");

        // 使用 StringRedisTemplate 获取数据
        String age1 = stringRedisTemplate.opsForValue().get("age");
        System.out.println("age : " + age1);

        // 使用 RedisTemplate 获取数据
        String age2 = (String) redisTemplate.opsForValue().get("age");

        System.out.println("age : " + age2);
    }

我们来看下结果

Redis中你可能不知道的两个类

我们通过StringRedisTemplate获取到了我们想要的数据。我们再来看看客户端存储的数据格式是不是跟RedisTemplate是一样的。

Redis中你可能不知道的两个类

我们发现并不是,那么大家可能要问了,那么我们究竟要在什么时候使用RedisTemplate,又在什么时候使用StringRedisTemplate呢?其实这个问题我也不好给大家太过准确的答案,毕竟我也刚用,我在网上看了很多博客,总结起来就是你在操作一个简单类型,比如说字符串这类数据的时候,可以考虑使用StringRedisTemplate,但是你要操作一些复杂的数据,比如说你要操作一个对象那么建议使用RedisTemplate。

END

更多精彩内容请关注”一个程序员的成长

Redis中你可能不知道的两个类
本人花费半年的时间总结的《Java面试指南》已拿腾讯等大厂offer,已开源在github ,欢迎star!

本文GitHub https://github.com/OUYANGSIHAI/JavaInterview 已收录,这是我花了6个月总结的一线大厂Java面试总结,本人已拿大厂offer,欢迎star

原文链接:blog.ouyangsihai.cn >> Redis中你可能不知道的两个类


 上一篇
Docker 基础 —— 镜像 Docker 基础 —— 镜像
作者:sparkdev链接://www.cnblogs.com/sparkdev 链接://www.cnblogs.com/sparkdev 镜像是 Docker 的三大核心概念之一。Docker
2021-04-05
下一篇 
【加精】深入学习Redis高可用架构——哨兵原理及实践 【加精】深入学习Redis高可用架构——哨兵原理及实践
在上篇文章《深入学习 Redis 高可用的基石:主从复制》中曾提到,Redis 主从复制的作用有数据热备、负载均衡、故障恢复等;但主从复制存在的一个问题是故障恢复无法自动化。 本文将要介绍的哨兵,它基于 Redis 主从复制,主要作
2021-04-05