StringRedisTemplate,RedisTemplate,Jedis,JedisPool如何区分和使用还在傻傻搞不懂?

博主小白最近刚在项目里接触redis,结果发现各种各样对redis进行操作的方式,当时就懵逼了,比如RedisTemplate,Jedis等等,好像对redis操作起来都挺方便呀,这哥几个到底啥关系呀???
一气之下各种查找资料…终于还算是搞懂了这哥几个不明不白的关系了…下面就来跟大家分享一下呀

1. Jedis

Jedis是Redis官方推荐的面向Java的操作Redis的客户端,听起来好像很牛逼…那么怎么来使用它呢??

首先要引入jedis依赖:

<dependency>
    <groupId>redis.clients</groupId>
    <artifactId>jedis</artifactId>
    <version>3.1.0</version>
</dependency>

引入依赖之后就可以直接进行使用啦

public static void main(String[] args){

    Jedis jedis = new Jedis("192.168.0.110",6379);

    jedis.set("hello","world");

    System.out.println(jedis.get("hello"));

}

当然,这里如果不指定ip和port也可以,只不过为默认的ip和port,可以看源码如下:(BinaryJedis是Jedis的父类

public BinaryJedis() {
    this.client = null;
    this.transaction = null;
    this.pipeline = null;
    this.dummyArray = new byte[0][];
    this.client = new Client();
}

(Connection是Client的父类,可以看到默认的ip和port

public class Connection implements Closeable {
    private static final byte[][] EMPTY_ARGS = new byte[0][];
    private String host = "localhost";
    private int port = 6379;
    //此处省略...
 }

可以看到jedis的使用还是很简单的呢…但是直接使用new的方式获取对象好像有点low…
而且需要注意的是!!!Jedis并不是线程安全的,在多线程使用同一个Jedis对象的时候会发生并发问题…这个时候JedisPool就出场啦

2. JedisPool

JedisPool类似于各种线程池,以及连接池,它是一个管理Jedis对象的池子,使Jedis对象恰到好处地被利用,既不过多创建,也不过少创建而导致多线程并发问题
那么它如何被使用呢???其实也很简单(当然有更复杂地需求另说啦…这里讲解的使用方法只是方便小白快速上手,需要更复杂的配置也可以评论区走起呀…我后续再出更复杂全面的JedisPool配置方式

需要的依赖同上~
public static void main(String[] args){
    //这里也可以省略ip和port不写,而使用默认的呀
    //具体可在JedisPool处按住Ctrl并点击查看JedisPool查看源码呀...
    JedisPool jedisPool = new JedisPool("192.168.0.110",6379);

    Jedis jedis = jedisPool.getResource();

    jedis.set("hello","world");

    System.out.println(jedis.get("hello"));
}

到这里,Jedis,JedisPool是啥就说明白啦,但是大家很快就会发现,怎么jedis.set(key,value)的value只能是字符串呢???我要是需要把其它类型作为value怎么办啊???

可见value为123时,它已经报错了…
这个时候就需要看一下源码啦

public String set(String key, String value) {
    this.checkIsInMultiOrPipeline();
    this.client.set(key, value);
    return this.client.getStatusCodeReply();
}

可以看到,value的类型为String,可能有小伙伴会认为123转为String也挺好转的啊,用String.valueOf(123)不就好了???可是如果我的value是一个对象怎么办呢??
嘿嘿,为了避免本篇文章篇幅过长,解决办法可以看这篇一款简单好用的序列化工具介绍

3. RedisTemplate

相信大家已经看的不奈烦了吧…我就是想知道jedis和RedisTemplate的区别,你BB这么多干啥呀???不急不急,一步一步来,区别马上就来啦*
小声BB:不知道具体如何使用,以及它们使用上的区别,那就算知道概念上的区别又有什么用呢?
通俗点说…为了让Spring框架体系能够更加方便的接入Redis的功能,RedisTemplate其实就是Spring框架对Jedis的封装…是 spring-data-redis中使用redis的模版
那么如何对它进行使用呢???

首先还是要先引入依赖

<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-data-redis</artifactId>
</dependency>

其次在yml/properties文件中进行配置

redis:
  host: 192.168.0.110
  port: 6379

然后就可以直接对其使用啦,如下:

@Resource
private RedisTemplate<String,Map<String,Integer>> redisTemplate;
//存数据 key为123456,value为map 类型为Map<String,Integer>
redisTemplate.opsForValue().set("123456",map);
//以123456为key取数据
redisTemplate.opsForValue().get("123456");

到这里,大家有没有发现这次value为map,竟然没有报错呢?
这是因为RedisTemplate使用了JdkSerializationRedisSerializer,在存入数据时会将数据先序列化成字节数组然后再存入Redis数据库
在这里插入图片描述可以看到红色箭头处的key:123456已经被序列化成字节数组了,可能会出现的问题就是用exists判断这个key是否存在时,显示不存在,但是在使用redisTemplate.opsForValue().get(“123456”)语句获取map时,返回的还是一个map,而不是字节化数组。也就是说,我们在存储数据时并不需要担心序列化的问题,redisTemplate自动进行序列化和反序列化。那么当我们存的key和value都为String类型的时候,我们想要在redis里直观地看到它们的值,应该怎么办呢?这个时候用StringRedisTemplate就比较方便啦,大家可能已经猜出了他们的关系…

4. StringRedisTemplate

首先我们可以来看看StringRedisTemplate和RedisTemplate之间的关系,还是贴源码:

public class StringRedisTemplate extends RedisTemplate<String, String> {
    public StringRedisTemplate() {
        this.setKeySerializer(RedisSerializer.string());
        this.setValueSerializer(RedisSerializer.string());
        this.setHashKeySerializer(RedisSerializer.string());
        this.setHashValueSerializer(RedisSerializer.string());
    }
    //此处省略...
 }

可以看到StringRedisTemplate继承于RedisTemplate,且重新设置了序列化方式,方式为StringRedisSerializer
毫无疑问,StringRedisTemplate的使用方式和RedisTemplate是一样的,且上图蓝色箭头处就是利用StringRedisTemplate存起来的数据。

到这里,这四者的关系和使用就说完啦,大家觉得有没有说明白的地方欢迎评论区提出来,觉得不错不妨点个赞呀~

发布了17 篇原创文章 · 获赞 12 · 访问量 8310

猜你喜欢

转载自blog.csdn.net/Sun_Dean/article/details/104066036