redis的集成与应用

springBoot集成redis

  • 引入redis的jar包
	<dependency>
			<groupId>org.springframework.boot</groupId>
			<artifactId>spring-boot-starter-data-redis</artifactId>
			<version>2.0.5.RELEASE</version>
		</dependency>
  • yml配置
spring:
  redis:
    port:             #redis的端口号默认端口是6379
    password:        #密码
    host: 127.0.0.1
    timeout: 5000
  • config
@Configuration
public class RedisConfig {

    @Bean
    public RedisTemplate redisTemplate(RedisConnectionFactory redisConnectionFactory) {
        //创建RedisTemplate模板对象
        RedisTemplate<String, Object> template = new RedisTemplate<>();
        //将redis的连接工厂与对象绑定
        template.setConnectionFactory(redisConnectionFactory);

        Jackson2JsonRedisSerializer jackson2JsonRedisSerializer = new Jackson2JsonRedisSerializer(Object.class);
        ObjectMapper om = new ObjectMapper();
        om.setVisibility(PropertyAccessor.ALL, JsonAutoDetect.Visibility.ANY);
        om.enableDefaultTyping(ObjectMapper.DefaultTyping.NON_FINAL);
        jackson2JsonRedisSerializer.setObjectMapper(om);

        StringRedisSerializer stringRedisSerializer = new StringRedisSerializer();
        // key采用String的序列化方式
        template.setKeySerializer(stringRedisSerializer);
        // value序列化方式采用jackson
        template.setValueSerializer(jackson2JsonRedisSerializer);

        // hash的key也采用String的序列化方式,需要配置一下StringSerializer,不然key会乱码 /XX/XX
        template.setHashKeySerializer(stringRedisSerializer);
        // hash的value序列化方式采用jackson
        template.setHashValueSerializer(jackson2JsonRedisSerializer);

        template.afterPropertiesSet();
        return template;

    }
}
  • 示例
    @Resource
    private  RedisTemplate redisTemplate;


    /**
     * 获取redis的数据
     * @return
     */
    public Boolean getRedisImg() {
        String o = (String) redisTemplate.opsForValue().get(log);
        if (StringUtils.isEmpty(o)) {
            return false;
        }
        return true;
    }

    /**
     * 生成key
     * @return
     */
    public Boolean doRedisImg() {
        redisTemplate.opsForValue().set(log,"你好");
        return true;
    }

redisTemplate常用API:

package com.hl.chapter29.web;
 
import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONObject;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.redis.core.*;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.*;
 
import javax.servlet.http.HttpServletRequest;
import java.io.IOException;
import java.util.*;
import java.util.concurrent.TimeUnit;
 
/**
 * 测试接口
 */
@Controller
public class DemoController {
 
    @Autowired
    private RedisTemplate redisTemplate;
 
    /**
     * String类型
     */
    @PostMapping(value = "/string")
    @ResponseBody
    public String stringTest(HttpServletRequest request, @RequestBody String req) {
 
        // 插入一个key值
        redisTemplate.opsForValue().set("a", 1000);
        // 判断是否有key对应的值,有返回true,没有返回false
        boolean isExist = redisTemplate.hasKey("a");
        System.out.println(isExist);
        // 取出key对应的值
        redisTemplate.opsForValue().get("a");
        // 删除某个key
        redisTemplate.delete("a");
        // 批量删除key
        List keys = new ArrayList<String>();
        keys.add("a");
        keys.add("b");
        redisTemplate.delete(keys);
        // 将当前传入的key值序列化为btye[]类型
        redisTemplate.opsForValue().set("b", 2000);
        System.out.println(redisTemplate.dump("b"));
        // 设置过期时间
        redisTemplate.expire("b", 10000, TimeUnit.MILLISECONDS);
//        System.out.println(redisTemplate.expireAt("b", new Date()));
 
        // 查找匹配的key值,返回set集合
        redisTemplate.opsForValue().set("a", 1100);
        redisTemplate.opsForValue().set("c", 3000);
        System.out.println(redisTemplate.keys("*"));
 
        // 修改key名称
        redisTemplate.rename("a", "aa");
 
        // 返回传入key存储的数据类型
        System.out.println(redisTemplate.type("aa"));
 
        // 随机取出一个key
        System.out.println(redisTemplate.randomKey());
 
        // 返回当前key剩余过期时间
        System.out.println(redisTemplate.getExpire("aa"));
        System.out.println(redisTemplate.getExpire("aa", TimeUnit.SECONDS));
 
        // 将key持久化
        redisTemplate.persist("c");
 
        // 将当前key迁移到指定数据库中
        redisTemplate.move("c", 1);
 
        // 返回部分字符
        System.out.println(redisTemplate.opsForValue().get("a", 0, 2));
 
        // 批量获取值
        List keys2 = new ArrayList();
        keys2.add("a");
        keys2.add("b");
        keys2.add("c");
        System.out.println(redisTemplate.opsForValue().multiGet(keys2));
 
        // 新增字符串
        redisTemplate.opsForValue().append("a", "1000");
 
        // 如果对应的map集合名称不存在,则添加否则不做修改
        Map valueMap = new HashMap();
        valueMap.put("valueMap1", "map1");
        valueMap.put("valueMap2", "map2");
        valueMap.put("valueMap3", "map3");
        redisTemplate.opsForValue().multiSetIfAbsent(valueMap);
 
        // 设置map集合到redis
        Map valueMap2 = new HashMap();
        valueMap2.put("valueMap1", "map1");
        valueMap2.put("valueMap2", "map2");
        valueMap2.put("valueMap3", "map3");
        redisTemplate.opsForValue().multiSet(valueMap2);
 
        // 获取字符串的长度
        redisTemplate.opsForValue().size("a");
 
        // 重新设置key对应的值,如果存在返回false,否则返回true
        redisTemplate.opsForValue().setIfAbsent("a", 33);
 
        // 将值 value 关联到 key,并将 key 的过期时间设为 timeout
        redisTemplate.opsForValue().set("a", 2000, 10, TimeUnit.HOURS);
 
        // 将二进制第offset位值变为value
//        redisTemplate.opsForValue().setBit(key, offset, value);
 
        // 对key所储存的字符串值,获取指定偏移量上的位(bit)
//        redisTemplate.opsForValue().getBit(key, offset);
 
 
        return JSONObject.parseObject(req).toJSONString();
    }
 
    /**
     * hash类型
     */
    @RequestMapping(value = "/hash")
    @ResponseBody
    public String hashTest(HttpServletRequest request) {
 
        // 新增hashMap值
        redisTemplate.opsForHash().put("hash", "a", "第一个");
 
        // 获取指定map键是否有值,有就返回,没有返回null
        System.out.println(redisTemplate.opsForHash().get("hash", "a"));
 
        // 获取指定key中所有键值对
        redisTemplate.opsForHash().put("hash", "b", "第二个");
        redisTemplate.opsForHash().put("hash", "c", "第三个");
        System.out.println(redisTemplate.opsForHash().entries("hash"));
 
        // 以Map集合的方式添加键值对
        Map map = new HashMap<String, String>();
        map.put("d", "第四个");
        map.put("e", "第五个");
        redisTemplate.opsForHash().putAll("hash", map);
        System.out.println(redisTemplate.opsForHash().entries("hash"));
 
        // 仅当hashKey不存在时才设置
        redisTemplate.opsForHash().putIfAbsent("hash", "a", "不是第一个了");
        redisTemplate.opsForHash().putIfAbsent("hash", "f", "第六个");
        System.out.println(redisTemplate.opsForHash().entries("hash"));
 
        // 删除一个或多个hash表字段
        redisTemplate.opsForHash().delete("hash", "e", "f");
        System.out.println(redisTemplate.opsForHash().entries("hash"));
 
        // 查看hash表中指定字段是否存在
        System.out.println(redisTemplate.opsForHash().hasKey("hash", "f"));
 
        // 给hash表中指定字段的整数值加上增量increment
        redisTemplate.opsForHash().put("hash", "e", 10);
        redisTemplate.opsForHash().increment("hash", "e", 10);
        System.out.println(redisTemplate.opsForHash().get("hash", "e"));
 
        // 给hash表中指定字段的浮点值加上increment
//        redisTemplate.opsForHash().put("hash", "f", 15.5);
//        redisTemplate.opsForHash().increment("hash", "f", 21.1);
//        System.out.println(redisTemplate.opsForHash().get("hash", "f"));
 
        // 获取hash表中所有字段
        System.out.println(redisTemplate.opsForHash().keys("hash"));
 
        // 获取hash表中字段数量
        System.out.println(redisTemplate.opsForHash().size("hash"));
 
        // 获取hash表中存在的所有值
        System.out.println(redisTemplate.opsForHash().values("hash"));
 
        // 匹配获取键值对
        try {
            Cursor<Map.Entry<Object, Object>> cursor = redisTemplate.opsForHash().scan("hash", ScanOptions.NONE);
            while (cursor.hasNext()) {
                Map.Entry<Object, Object> entry = cursor.next();
                Object key = entry.getKey();
                Object value = entry.getValue();
                System.out.println(key + ": " + value);
            }
            cursor.close();
        } catch (IOException e) {
            e.printStackTrace();
        }
 
        return null;
 
    }
 
    /**
     * list类型
     */
    @RequestMapping(value = "/list")
    @ResponseBody
    public String listTest(HttpServletRequest request) {
 
        // 向列表中头部添加元素
        redisTemplate.opsForList().leftPush("list", "第一个list元素");
        // 通过index获取列表中的元素
        System.out.println(redisTemplate.opsForList().index("list", 0));
 
        // 把多个值存入列表头部
        redisTemplate.opsForList().leftPushAll("list", "第二个list元素", "第三个list元素", "第四个list元素");
 
        // 获取列表指定范围内元素,start起始位置,end结束位置,-1返回所有
        System.out.println(redisTemplate.opsForList().range("list", 0, 3));
 
        // list存在的时候再加入
        redisTemplate.opsForList().leftPushIfPresent("list", "第六个list元素");
        System.out.println(redisTemplate.opsForList().range("list", 0, -1));
 
        // 在pivot值存在时在pivot前面添加
        redisTemplate.opsForList().leftPush("list", "第六个list元素", "第五个半list元素");
        System.out.println(redisTemplate.opsForList().range("list", 0, -1));
 
        // 按照先进先出的原则添加多个值
        redisTemplate.opsForList().rightPush("list", "第七个list元素");
        redisTemplate.opsForList().rightPushAll("list", "第八个list元素", "第九个list元素");
        System.out.println(redisTemplate.opsForList().range("list", 0, -1));
 
        // 在pivot右边添加值
        redisTemplate.opsForList().rightPush("list", "第七个list元素", "第七个半list元素");
        System.out.println(redisTemplate.opsForList().range("list", 0, -1));
 
        // 设置指定索引处元素的值
        redisTemplate.opsForList().set("list", 5, "修改后的list元素");
 
        // 移除并获取列表中第一个元素
        System.out.println(redisTemplate.opsForList().leftPop("list"));
        System.out.println(redisTemplate.opsForList().leftPop("list", 10, TimeUnit.SECONDS));
 
        // 移除并获取列表中最后一个元素
        System.out.println(redisTemplate.opsForList().rightPop("list"));
        System.out.println(redisTemplate.opsForList().rightPop("list", 8, TimeUnit.SECONDS));
 
        // 从一个列表右边弹出一个元素并将该元素插入另一个列表的左边
        redisTemplate.opsForList().rightPopAndLeftPush("list", "list2");
        redisTemplate.opsForList().rightPopAndLeftPush("list", "list2", 10, TimeUnit.SECONDS);
 
        // 删除列表中值等于指定value的元素,index=0删除所有,index>0删除头部开始第一个,index<0删除尾部开始第一个
        redisTemplate.opsForList().remove("list", 0, "第三个list元素");
        System.out.println(redisTemplate.opsForList().range("list", 0, -1));
 
        // 列表进行裁剪
        redisTemplate.opsForList().trim("list", 1, 4);
        System.out.println(redisTemplate.opsForList().range("list", 0, -1));
 
        // 获取当前列表长度
        System.out.println(redisTemplate.opsForList().size("list"));
 
        return null;
    }
 
    /**
     * set类型
     */
    @GetMapping(value = "/set")
    @ResponseBody
    public String setTest(HttpServletRequest request) {
        // 添加元素
        redisTemplate.opsForSet().add("set", "第一个set元素");
        redisTemplate.opsForSet().add("set", "第二个set元素");
        redisTemplate.opsForSet().add("set", "第三个set元素");
        redisTemplate.opsForSet().add("set", "第四个set元素");
        redisTemplate.opsForSet().add("set", "第五个set元素");
 
        // 获取集合中所有元素
        System.out.println(redisTemplate.opsForSet().members("set"));
 
        // 移除元素
        redisTemplate.opsForSet().remove("set", "第一个set元素", "第三个set元素");
        System.out.println(redisTemplate.opsForSet().members("set"));
 
        // 删除并返回一个随机元素
        System.out.println(redisTemplate.opsForSet().pop("set"));
 
 
        // 获取集合大小
        System.out.println(redisTemplate.opsForSet().size("set"));
 
        // 判断集合是否包含value
        System.out.println(redisTemplate.opsForSet().isMember("set", "第四个set元素"));
 
        redisTemplate.opsForSet().add("otherSet", "第一个set元素");
        redisTemplate.opsForSet().add("otherSet", "第二个set元素");
        redisTemplate.opsForSet().add("otherSet", "第三个set元素");
        redisTemplate.opsForSet().add("otherSet", "第四个set元素");
        // 获取两个集合的交集
        System.out.println(redisTemplate.opsForSet().intersect("set", "otherSet"));
 
        // 获取多个集合的交集
        redisTemplate.opsForSet().add("thirdSet", "第二个set元素");
        Set otherKeys = new HashSet();
        otherKeys.add("otherSet");
        otherKeys.add("thirdSet");
        System.out.println(redisTemplate.opsForSet().intersect("set", otherKeys));
 
        // set集合与otherSet集合的交集存储到targetSet集合中
        redisTemplate.opsForSet().intersectAndStore("set", "otherSet", "targetSet");
        System.out.println(redisTemplate.opsForSet().members("targetSet"));
 
        // set集合与多个集合的交集存储到targetSet集合中
        redisTemplate.opsForSet().intersectAndStore("set", otherKeys, "targetSet");
        System.out.println(redisTemplate.opsForSet().members("targetSet"));
 
        // 获取两个或者多个集合的并集
        System.out.println(redisTemplate.opsForSet().union("set", "otherSet"));
        System.out.println(redisTemplate.opsForSet().union("set", otherKeys));
 
        // set集合与多个集合的并集存储到targetSet集合中
        redisTemplate.opsForSet().unionAndStore("set", otherKeys, "targetSet2");
        System.out.println(redisTemplate.opsForSet().members("targetSets"));
 
        // 获取两个或者多个集合的差集
        System.out.println(redisTemplate.opsForSet().difference("set", otherKeys));
 
        // 差集存储到targetSet中
        redisTemplate.opsForSet().unionAndStore("set", otherKeys, "targetSet3");
        System.out.println(redisTemplate.opsForSet().members("targetSet3"));
 
        // 随机获取集合中的一个元素
        System.out.println(redisTemplate.opsForSet().randomMember("set"));
 
        // 随机获取集合中若干个元素
        System.out.println(redisTemplate.opsForSet().randomMembers("set", 5));
 
        // 遍历set,类似于iterator
        try {
            Cursor<Map.Entry<Object, Object>> cursor = redisTemplate.opsForSet().scan("set", ScanOptions.NONE);
            while (cursor.hasNext()) {
                System.out.println(cursor.next());
            }
            cursor.close();
        } catch (IOException e) {
            e.printStackTrace();
        }
 
 
        return null;
    }
 
    /**
     * zset类型
     */
    @GetMapping(value = "/zset")
    @ResponseBody
    public String zsetTest(HttpServletRequest request) {
        // 添加元素,有序集合按照score的值从小到大排序
        redisTemplate.opsForZSet().add("zset", "第一个zset", 100);
        redisTemplate.opsForZSet().add("zset", "第二个zset", 110);
        redisTemplate.opsForZSet().add("zset", "第三个zset", 120);
        redisTemplate.opsForZSet().add("zset", "第四个zset", 130);
        redisTemplate.opsForZSet().add("zset", "第五个zset", 140);
 
        // 获取元素在集合中的排名,按照score值从小到大排序
        System.out.println("从小到大:" + redisTemplate.opsForZSet().rank("zset", "第二个zset"));
 
        // 获取元素在集合中的排名,按照score值从大到小排序
        System.out.println("从大到小:" + redisTemplate.opsForZSet().reverseRank("zset", "第二个zset"));
 
        System.out.println("--------------------------------------");
 
        // 获取集合中给定区间的元素,start开始位置,end结束位置,-1查询所有(从小到大)
        // 返回值为:Set<ZSetOperations.TypedTuple<V>>
        Iterator iterator = redisTemplate.opsForZSet().rangeWithScores("zset", 0, -1).iterator();
        while (iterator.hasNext()) {
            ZSetOperations.TypedTuple typedTuple = (ZSetOperations.TypedTuple) iterator.next();
            System.out.println("从小到大:" + typedTuple.getValue() + ", " + typedTuple.getScore());
        }
 
        System.out.println("--------------------------------------");
 
        // 获取集合中给定区间的元素,start开始位置,end结束位置,-1查询所有(从大到小)
        Iterator iterator3 = redisTemplate.opsForZSet().reverseRangeWithScores("zset", 0, -1).iterator();
        while (iterator3.hasNext()) {
            ZSetOperations.TypedTuple typedTuple3 = (ZSetOperations.TypedTuple) iterator3.next();
            System.out.println("从大到小:" + typedTuple3.getValue() + ", " + typedTuple3.getScore());
        }
 
        System.out.println("--------------------------------------");
 
        // 按照score值查询集合中的元素,结果从小到大排序
        System.out.println("从小到大:" + redisTemplate.opsForZSet().rangeByScore("zset", 100, 200));
        Iterator iterator4 = redisTemplate.opsForZSet().rangeByScoreWithScores("zset", 100, 200).iterator();
        while (iterator4.hasNext()) {
            ZSetOperations.TypedTuple typedTuple4 = (ZSetOperations.TypedTuple) iterator4.next();
            System.out.println("从小到大:" + typedTuple4.getValue() + ", " + typedTuple4.getScore());
        }
 
        System.out.println("--------------------------------------");
 
 
        // 按照score值查询集合中的元素,结果从大到小排序
        System.out.println("从大到小:" + redisTemplate.opsForZSet().reverseRangeByScore("zset", 100, 200));
        Iterator iterator5 = redisTemplate.opsForZSet().reverseRangeByScoreWithScores("zset", 100, 200).iterator();
        while (iterator5.hasNext()) {
            ZSetOperations.TypedTuple typedTuple5 = (ZSetOperations.TypedTuple) iterator5.next();
            System.out.println("从大到小:" + typedTuple5.getValue() + ", " + typedTuple5.getScore());
        }
 
        System.out.println("--------------------------------------");
 
        // 从大到小排序获取集合中score在给定最大最小范围内的元素
        System.out.println("从大到小:" + redisTemplate.opsForZSet().reverseRangeByScore("zset", 100, 1000, 0, -1));
 
        System.out.println("--------------------------------------");
 
        // 根据score获取集合元素数量
        System.out.println(redisTemplate.opsForZSet().count("zset", 100, 150));
 
        System.out.println("--------------------------------------");
 
        // 获取集合大小
        System.out.println(redisTemplate.opsForZSet().size("zset"));
        System.out.println(redisTemplate.opsForZSet().zCard("zset"));
 
        System.out.println("--------------------------------------");
 
        // 获取集合中key value 对应的score
        System.out.println(redisTemplate.opsForZSet().score("zset", "第三个zset"));
 
        System.out.println("--------------------------------------");
 
        // 移除指定索引位置的元素
        redisTemplate.opsForZSet().removeRange("zset", 0, 1);
        System.out.println(redisTemplate.opsForZSet().range("zset", 0, -1));
 
        System.out.println("--------------------------------------");
 
        // 获取key 和otherKey的交集并存储在targetKey
        redisTemplate.opsForZSet().add("otherZset", "第二个zset", 200);
        redisTemplate.opsForZSet().add("otherZset", "第三个zset", 200);
        redisTemplate.opsForZSet().intersectAndStore("zset", "otherZset", "targetZset");
        System.out.println(redisTemplate.opsForZSet().range("targetZset", 0, -1));
 
        System.out.println("--------------------------------------");
 
        // 获取key和otherKey的并集并且存储在targetKey中
        redisTemplate.opsForZSet().unionAndStore("zset", "otherZset", "fourthZset");
        System.out.println(redisTemplate.opsForZSet().range("fourthZset", 0, -1));
 
        System.out.println("--------------------------------------");
 
        // 遍历集合
        try {
            Cursor<ZSetOperations.TypedTuple> cursor = redisTemplate.opsForZSet().scan("zset", ScanOptions.NONE);
            while (cursor.hasNext()) {
                ZSetOperations.TypedTuple typedTuple = cursor.next();
                System.out.println(typedTuple.getValue() + ", " + typedTuple.getScore());
            }
            cursor.close();
        } catch (IOException e) {
            e.printStackTrace();
        }
 
        return null;
    }
 
}

redis的工具类

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.stereotype.Component;
import org.springframework.util.CollectionUtils;

import java.util.List;
import java.util.Map;
import java.util.Set;
import java.util.concurrent.TimeUnit;

/**
 * Redis工具类
 *
 *
 */
@Component
public final class RedisUtil {

    @Autowired
    private RedisTemplate<String, Object> redisTemplate;


    /**
     * 指定缓存失效时间
     *
     * @param key  键
     * @param time 时间(秒)
     * @return true 成功 false 失败
     */
    public boolean expire(String key, long time) {
        try {
            if (time > 0) {
                redisTemplate.expire(key, time, TimeUnit.SECONDS);
            }
            return true;
        } catch (Exception e) {
            e.printStackTrace();
            return false;
        }
    }

    /**
     * 根据key 获取过期时间
     *
     * @param key 键 不能为null
     * @return 时间(秒) 返回0代表为永久有效
     */
    public long getExpire(String key) {
        return redisTemplate.getExpire(key, TimeUnit.SECONDS);
    }

    /**
     * 判断key是否存在
     *
     * @param key 键
     * @return true 存在 false不存在
     */
    public boolean hasKey(String key) {
        try {
            return redisTemplate.hasKey(key);
        } catch (Exception e) {
            e.printStackTrace();
            return false;
        }
    }

    /**
     * 删除缓存
     *
     * @param key 可以传一个值 或多个
     */
    @SuppressWarnings("unchecked")
    public void del(String... key) {
        if (key != null && key.length > 0) {
            if (key.length == 1) {
                redisTemplate.delete(key[0]);
            } else {
                redisTemplate.delete(CollectionUtils.arrayToList(key));
            }
        }
    }

    // ============================String=============================

    /**
     * 普通缓存获取
     *
     * @param key 键
     * @return 值
     */
    public Object get(String key) {
        return key == null ? null : redisTemplate.opsForValue().get(key);
    }

    public <T> T get(String key, Class<T> clazz) {
        Object obj = key == null ? null : redisTemplate.opsForValue().get(key);
        if (clazz.isInstance(obj)) {
            return clazz.cast(obj);
        }
        return null;
    }

    /**
     * 普通缓存放入
     *
     * @param key   键
     * @param value 值
     * @return true成功 false失败
     */
    public boolean set(String key, Object value) {
        try {
            redisTemplate.opsForValue().set(key, value);
            return true;
        } catch (Exception e) {
            e.printStackTrace();
            return false;
        }

    }


    /**
     * 普通缓存放入并设置时间
     *
     * @param key   键
     * @param value 值
     * @param time  时间(秒) time要大于0 如果time小于等于0 将设置无限期
     * @return true成功 false 失败
     */
    public boolean set(String key, Object value, long time) {
        try {
            if (time > 0) {
                redisTemplate.opsForValue().set(key, value, time, TimeUnit.SECONDS);
            } else {
                set(key, value);
            }
            return true;
        } catch (Exception e) {
            e.printStackTrace();
            return false;
        }

    }

    /**
     * 如果key已存在就不执行,并返回false 不存在就执行 并返回true
     *
     * @param key
     * @param value
     * @return true成功 false失败
     */
    public Boolean setNx(String key, Object value) {
        return redisTemplate.opsForValue().setIfAbsent(key, value);
    }

    /**
     * 如果key已存在就不执行,并返回false 不存在就执行 并返回true
     *
     * @param key
     * @param value
     * @return true成功 false失败
     */
    public Boolean setNx(String key, Object value, long time) {
        return redisTemplate.opsForValue().setIfAbsent(key, value, time, TimeUnit.SECONDS);
    }


    /**
     * 如果key已存在就执行,并返回true 不存在就不执行 并返回false
     *
     * @param key
     * @param value
     * @return true成功 false失败
     */
    public Boolean setXx(String key, Object value) {
        return redisTemplate.opsForValue().setIfPresent(key, value);
    }

    /**
     * 如果key已存在就执行,并返回true 不存在就不执行 并返回false
     *
     * @param key
     * @param value
     * @return true成功 false失败
     */
    public Boolean setXx(String key, Object value, long time) {
        return redisTemplate.opsForValue().setIfPresent(key, value, time, TimeUnit.SECONDS);

    }

    /**
     * 递增
     *
     * @param key   键
     * @param delta 要增加几(大于0)
     * @return
     */
    public long incr(String key, long delta) {
        if (delta < 0) {
            throw new RuntimeException("递增因子必须大于0");
        }
        return redisTemplate.opsForValue().increment(key, delta);
    }

    /**
     * 递减
     *
     * @param key   键
     * @param delta 要减少几(小于0)
     * @return
     */
    public long decr(String key, long delta) {
        if (delta < 0) {
            throw new RuntimeException("递减因子必须大于0");
        }
        return redisTemplate.opsForValue().increment(key, -delta);
    }

    // ================================Map=================================

    /**
     * HashGet
     *
     * @param key  键 不能为null
     * @param item 项 不能为null
     * @return 值
     */
    public Object hget(String key, String item) {
        return redisTemplate.opsForHash().get(key, item);
    }

    /**
     * 获取hashKey对应的所有键值
     *
     * @param key 键
     * @return 对应的多个键值
     */
    public Map<Object, Object> hmget(String key) {
        return redisTemplate.opsForHash().entries(key);
    }

    /**
     * HashSet
     *
     * @param key 键
     * @param map 对应多个键值
     * @return true 成功 false 失败
     */
    public boolean hmset(String key, Map<String, Object> map) {
        try {
            redisTemplate.opsForHash().putAll(key, map);
            return true;
        } catch (Exception e) {
            e.printStackTrace();
            return false;
        }
    }

    /**
     * HashSet 并设置时间
     *
     * @param key  键
     * @param map  对应多个键值
     * @param time 时间(秒)
     * @return true成功 false失败
     */
    public boolean hmset(String key, Map<String, Object> map, long time) {
        try {
            redisTemplate.opsForHash().putAll(key, map);
            if (time > 0) {
                expire(key, time);
            }
            return true;
        } catch (Exception e) {
            e.printStackTrace();
            return false;
        }
    }

    /**
     * 向一张hash表中放入数据,如果不存在将创建
     *
     * @param key   键
     * @param item  项
     * @param value 值
     * @return true 成功 false失败
     */
    public boolean hset(String key, String item, Object value) {
        try {
            redisTemplate.opsForHash().put(key, item, value);
            return true;
        } catch (Exception e) {
            e.printStackTrace();
            return false;
        }
    }

    /**
     * 向一张hash表中放入数据,如果不存在将创建
     *
     * @param key   键
     * @param item  项
     * @param value 值
     * @param time  时间(秒) 注意:如果已存在的hash表有时间,这里将会替换原有的时间
     * @return true 成功 false失败
     */
    public boolean hset(String key, String item, Object value, long time) {
        try {
            redisTemplate.opsForHash().put(key, item, value);
            if (time > 0) {
                expire(key, time);
            }
            return true;
        } catch (Exception e) {
            e.printStackTrace();
            return false;
        }
    }

    /**
     * 删除hash表中的值
     *
     * @param key  键 不能为null
     * @param item 项 可以使多个 不能为null
     */
    public void hdel(String key, Object... item) {
        redisTemplate.opsForHash().delete(key, item);
    }

    /**
     * 判断hash表中是否有该项的值
     *
     * @param key  键 不能为null
     * @param item 项 不能为null
     * @return true 存在 false不存在
     */
    public boolean hHasKey(String key, String item) {
        return redisTemplate.opsForHash().hasKey(key, item);
    }

    /**
     * hash递增 如果不存在,就会创建一个 并把新增后的值返回
     *
     * @param key  键
     * @param item 项
     * @param by   要增加几(大于0)
     * @return
     */
    public double hincr(String key, String item, double by) {
        return redisTemplate.opsForHash().increment(key, item, by);
    }

    /**
     * hash递减
     *
     * @param key  键
     * @param item 项
     * @param by   要减少记(小于0)
     * @return
     */
    public double hdecr(String key, String item, double by) {
        return redisTemplate.opsForHash().increment(key, item, -by);
    }

    // ============================set=============================

    /**
     * 根据key获取Set中的所有值
     *
     * @param key 键
     * @return
     */
    public Set<Object> sGet(String key) {
        try {
            return redisTemplate.opsForSet().members(key);
        } catch (Exception e) {
            e.printStackTrace();
            return null;
        }
    }

    /**
     * 根据value从一个set中查询,是否存在
     *
     * @param key   键
     * @param value 值
     * @return true 存在 false不存在
     */
    public boolean sHasKey(String key, Object value) {
        try {
            return redisTemplate.opsForSet().isMember(key, value);
        } catch (Exception e) {
            e.printStackTrace();
            return false;
        }
    }

    /**
     * 将数据放入set缓存
     *
     * @param key    键
     * @param values 值 可以是多个
     * @return 成功个数
     */
    public long sSet(String key, Object... values) {
        try {
            return redisTemplate.opsForSet().add(key, values);
        } catch (Exception e) {
            e.printStackTrace();
            return 0;
        }
    }

    /**
     * 将set数据放入缓存
     *
     * @param key    键
     * @param time   时间(秒)
     * @param values 值 可以是多个
     * @return 成功个数
     */
    public long sSetAndTime(String key, long time, Object... values) {
        try {
            Long count = redisTemplate.opsForSet().add(key, values);
            if (time > 0)
                expire(key, time);
            return count;
        } catch (Exception e) {
            e.printStackTrace();
            return 0;
        }
    }

    /**
     * 获取set缓存的长度
     *
     * @param key 键
     * @return
     */
    public long sGetSetSize(String key) {
        try {
            return redisTemplate.opsForSet().size(key);
        } catch (Exception e) {
            e.printStackTrace();
            return 0;
        }
    }

    /**
     * 移除值为value的
     *
     * @param key    键
     * @param values 值 可以是多个
     * @return 移除的个数
     */
    public long setRemove(String key, Object... values) {
        try {
            Long count = redisTemplate.opsForSet().remove(key, values);
            return count;
        } catch (Exception e) {
            e.printStackTrace();
            return 0;
        }
    }
    // ===============================list=================================

    /**
     * 获取list缓存的内容
     *
     * @param key   键
     * @param start 开始
     * @param end   结束 0 到 -1代表所有值
     * @return
     */
    public List<Object> lGet(String key, long start, long end) {
        try {
            return redisTemplate.opsForList().range(key, start, end);
        } catch (Exception e) {
            e.printStackTrace();
            return null;
        }
    }

    /**
     * 获取list缓存的长度
     *
     * @param key 键
     * @return
     */
    public long lGetListSize(String key) {
        try {
            return redisTemplate.opsForList().size(key);
        } catch (Exception e) {
            e.printStackTrace();
            return 0;
        }
    }

    /**
     * 通过索引 获取list中的值
     *
     * @param key   键
     * @param index 索引 index>=0时, 0 表头,1 第二个元素,依次类推;index<0时,-1,表尾,-2倒数第二个元素,依次类推
     * @return
     */
    public Object lGetIndex(String key, long index) {
        try {
            return redisTemplate.opsForList().index(key, index);
        } catch (Exception e) {
            e.printStackTrace();
            return null;
        }
    }

    /**
     * 将list放入缓存
     *
     * @param key   键
     * @param value 值
     * @return
     */
    public boolean lSet(String key, Object value) {
        try {
            redisTemplate.opsForList().rightPush(key, value);
            return true;
        } catch (Exception e) {
            e.printStackTrace();
            return false;
        }
    }

    /**
     * 将list放入缓存
     *
     * @param key   键
     * @param value 值
     * @param time  时间(秒)
     * @return
     */
    public boolean lSet(String key, Object value, long time) {
        try {
            redisTemplate.opsForList().rightPush(key, value);
            if (time > 0)
                expire(key, time);
            return true;
        } catch (Exception e) {
            e.printStackTrace();
            return false;
        }
    }

    /**
     * 将list放入缓存
     *
     * @param key   键
     * @param value 值
     * @return
     */
    public boolean lSet(String key, List<Object> value) {
        try {
            redisTemplate.opsForList().rightPushAll(key, value);
            return true;
        } catch (Exception e) {
            e.printStackTrace();
            return false;
        }
    }

    /**
     * 将list放入缓存
     *
     * @param key   键
     * @param value 值
     * @param time  时间(秒)
     * @return
     */
    public boolean lSet(String key, List<Object> value, long time) {
        try {
            redisTemplate.opsForList().rightPushAll(key, value);
            if (time > 0)
                expire(key, time);
            return true;
        } catch (Exception e) {
            e.printStackTrace();
            return false;
        }
    }

    /**
     * 根据索引修改list中的某条数据
     *
     * @param key   键
     * @param index 索引
     * @param value 值
     * @return
     */
    public boolean lUpdateIndex(String key, long index, Object value) {
        try {
            redisTemplate.opsForList().set(key, index, value);
            return true;
        } catch (Exception e) {
            e.printStackTrace();
            return false;
        }
    }

    /**
     * 移除N个值为value
     *
     * @param key   键
     * @param count 移除多少个
     * @param value 值
     * @return 移除的个数
     */
    public long lRemove(String key, long count, Object value) {
        try {
            Long remove = redisTemplate.opsForList().remove(key, count, value);
            return remove;
        } catch (Exception e) {
            e.printStackTrace();
            return 0;
        }
    }
}




  • redis的windows配置简单介绍

找到redis.windows.conf中进行配置
protected-mode no // 改为no 不开启保护模式

port 6379 //redis端口号

daemonize yes // 开启守护线程 (redis关闭的时候也照样运行)

requirepass **** //设置redis的访问密码

#bind 127.0.0.1 只能本机访问 (关闭)

使用redis锁

导包

<dependency>
			<groupId>org.redisson</groupId>
			<artifactId>redisson</artifactId>
			<version>3.15.4</version>
		</dependency>

yml配置

spring:
  redis:
    port: 6379            #redis的端口号默认端口是6379
    password: 123456        #密码
    host: redis
    timeout: 5000
    database: 3

引入配置

package com.itllc.config.RedisConfig;

import org.apache.commons.lang3.StringUtils;
import org.redisson.Redisson;
import org.redisson.api.RedissonClient;
import org.redisson.config.Config;
import org.redisson.config.SingleServerConfig;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.cache.annotation.EnableCaching;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;

/**
 * @author lilinchun
 * @date 2022/7/7 0007 11:31
 */
@Configuration
@EnableCaching
public class RedissonConfig {
    @Value("${spring.redis.host}")
    String REDIS_HOST;

    @Value("${spring.redis.port}")
    String REDIS_PORT;

    @Value("${spring.redis.password}")
    String REDIS_PASSWORD;

    @Value("${spring.redis.database}")
    int REDIS_DATABASE;

    @Bean
    public RedissonClient redissonClient() {
        Config config = new Config();
        SingleServerConfig r = config.useSingleServer();
        r.setAddress("redis://" + REDIS_HOST + ":" + REDIS_PORT)
                .setDatabase(REDIS_DATABASE)
                .setConnectionMinimumIdleSize(5)
                .setConnectionPoolSize(10);
        if (!StringUtils.isEmpty(REDIS_PASSWORD)) {
            r.setPassword(REDIS_PASSWORD);
        }
        return Redisson.create(config);
    }

}

测试用例

 /**
     * redis消息发送
     *
     * @param message
     */
    @GetMapping(value = "/redisLock")
    @ApiOperation("redis锁测试")
    public Result<Boolean> redisLock(@NotBlank @ApiParam(value = "发送的消息",required = true) @RequestParam("message") String message) {
        String key = "redis_lock";
        RLock lock = redissonClient.getLock(key);//获取锁
        lock.lock();//加锁
        try {
            //业务放到try中
            String res = (String) redisTemplate.opsForValue().get("goods:001");
            int count = res == null ? 0 :Integer.parseInt(res);
            if(count > 0){
                int realCount = count - 1;//减库存
                //将库存设置到数据库
                redisTemplate.opsForValue().set("goods:001",String.valueOf(realCount));
                System.out.println("剩余库存:"+realCount+",服务的端口:");
            }else{
                System.out.println("库存没有了");
            }
        } finally {
            if(lock.isLocked() && lock.isHeldByCurrentThread()){
                lock.unlock();//解锁
            }
        }
        return new Result<>(true);
    }

redis注解缓存

平时大家使用redis一般都是直接存储key,value.
spring全家桶肯定帮大家想到了这一点.可以让大家方便的使用注解操作redis节省代码量.
总结:总共有三种方式,底层利用了spring的aop,并且方法返回的对象一定要实现序列化

  • @Cacheable:注解于方法上,第一次会把后面的cacheNames+key 拼接为key,把返回值序列化后作为value set到redis中去.后面再一次访问相同的key的时候就直接从redis中取值了,不会再访问这个方法
@Override
@Cacheable(cacheNames = "product",key = "#id")
public ProductInfo findOne(String id) {
   return productInfoRepository.findById(id).orElse(null);
}

  • @CachePut:每次都会把方法的返回值序列化之后set到redis中去(每次都会执行方法),即更新这个key对应的值
	@Override
    @CachePut(cacheNames = "product",key = "#productId")
    public ProductInfo onSale(String productId) {
        ProductInfo productInfo = this.findOne(productId);
        if(null == productInfo){
            throw new SellException(ResultEnum.PRODUCT_NOT_EXIST);
        }

        if(productInfo.getProductStatusEnum().getCode() == ProductStatusEnum.UP.getCode()){
            log.warn("[商品上架处理]-----商品已经是上架状态了,这里直接返回原ProductInfo={}",productInfo);
        }else {
            productInfo.setProductStatus(ProductStatusEnum.UP.getCode());
            productInfo = this.save(productInfo);
        }
        return productInfo;
    }

  • @CacheEvict:这个比较好理解,就是从redis中把这个key删除了
@Override
@CacheEvict(cacheNames = "product",key = "#productInfo.productId")
public ProductInfo save(ProductInfo productInfo) {
    return productInfoRepository.save(productInfo);
}

这里的key其实可以不写,比如上面的@CacheEvict中不写的话就会把参数默认为key,即下面的productInfo对象

一次驱逐多个redis的key

@Caching(evict={
			@CacheEvict(value = Cache.CONSTANT, key = "'" + CacheKey.SINGLE_ROLE_NAME + "'+#roleId"),
            @CacheEvict(value = Cache.CONSTANT, key = "'" + CacheKey.ROLES_NAME + "'+#roleId"),
            @CacheEvict(value = Cache.CONSTANT, key = "'" + CacheKey.SINGLE_ROLE_NAME + "'+#roleId")
            })
public ResponseData remove(@RequestParam Long roleId) {
………………
}

  1. 可以加在方法上使用@Cacheable set value到redis
    使用@Cacheable后,第一次会把后面的cacheNames+key 拼接为key,把返回值序列化后作为value set到redis中去.后面再一次访问相同的key的时候就直接从redis中取值了,不会再访问这个方法,也就不会再从数据库中取值了

可以把方法中的参数拼到key上,在这个方法运行完后会把这个方法的返回值根据@Cacheable注解中的cacheNames+key拼接后的值为key,set到redis中取,下次再访问这个key的时候直接从redis中取数据,不用去mysql查找一遍了

在这里插入图片描述

在这里插入图片描述

  • 使用condition,对传入的参数进行,筛选只允许符合条件的请求set到redis中
    对于现实的需求,肯定有些时候是异常请求,是不需要缓存到redis中的,这里我们也可以使用condition加上判断,判断通过的时候才允许缓存到redis
    在这里插入图片描述
  • 有根据请求筛选,那么自然也就有根据方法的结果筛选的,根据结果筛选可以使用unless
    在这里插入图片描述
    @Cacheable中,unless参数的作用是:函数返回值符合表达式条件的,veto(否决)、不缓存
    换句话说,函数返回值符合条件的排除掉、只缓存其余不符合条件的
  • 若是想要某种条件下才缓存,那么可以在el表达式中对其他情况取反就行了
    例如,想要返回结果中productId = 1的,那么可以这样写
    @Cacheable(cacheNames = “product111”,key = “#productInfo.productId”, unless = “!#result.productId.equals(‘1’)”)
    把结果中不等于1的排除掉,那么剩下的就是等于1了
    这里可能有点绕,因为unless自动在最外面取了个反,所以要双重否定
    简单说就是对你想要的结果取反,unless自己外面有取反!!2个取反就还是原先的结果
  • 使用@CacheConfig注解可以让多个方法使用统一的cacheNames

如果在同一个类中,要使用redis缓存的每个方法中都要写cacheNames是不是觉得很麻烦,可以使用@CacheConfig(cacheNames = “product”),为下面的注解默认使用上面这个CacheConfig中定义的cacheNames

这个和css中的作用域一样,如果方法上的注解有自己定义的cacheNames,那么最后生效的还是方法上自己定义的cacheNames,并不会强行使用类上CacheConfig定义的cacheNames

在这里插入图片描述

详情:redis注解缓存原文

redis缓存

新增RedisTemplate封装工具类 : 最全的 基于 RedisTemplate 封装的 RedisUtils 工具类

Redis 可以存储键与5种不同数据结构类型之间的映射,这5种数据结构类型分别为String(字符串)、List(列表)、Set(集合)、Hash(散列)和 Zset(有序集合)。

Redis的String数据结构
set void set(K key, V value);

redisTemplate.opsForValue().set("num","123");
redisTemplate.opsForValue().get("num")  输出结果为123

set void set(K key, V value, long timeout, TimeUnit unit);

redisTemplate.opsForValue().set("num","123",10, TimeUnit.SECONDS);
redisTemplate.opsForValue().get("num")设置的是10秒失效,十秒之内查询有结果,十秒之后返回为null

set void set(K key, V value, long offset);

覆写(overwrite)给定 key 所储存的字符串值,从偏移量 offset 开始

template.opsForValue().set("key","hello world");
template.opsForValue().set("key","redis", 6);
System.out.println("***************"+template.opsForValue().get("key"));
结果:***************hello redis

get V get(Object key);

template.opsForValue().set("key","hello world");
System.out.println("***************"+template.opsForValue().get("key"));
结果:***************hello world

getAndSet V getAndSet(K key, V value);

设置键的字符串值并返回其旧值

template.opsForValue().set("getSetTest","test");
System.out.println(template.opsForValue().getAndSet("getSetTest","test2"));
结果:test

append Integer append(K key, String value);

如果key已经存在并且是一个字符串,则该命令将该值追加到字符串的末尾。如果键不存在,则它被创建并设置为空字符串,因此APPEND在这种特殊情况下将类似于SET。

template.opsForValue().append("test","Hello");
System.out.println(template.opsForValue().get("test"));
template.opsForValue().append("test","world");
System.out.println(template.opsForValue().get("test"));
Hello
Helloworld

size Long size(K key);
返回key所对应的value值得长度

template.opsForValue().set("key","hello world");
System.out.println("***************"+template.opsForValue().size("key"));
***************11

Redis的List数据结构

Long size(K key);
返回存储在键中的列表的长度。如果键不存在,则将其解释为空列表,并返回0。当key存储的值不是列表时返回错误。

System.out.println(template.opsForList().size("list"));
6

Long leftPush(K key, V value);
将所有指定的值插入存储在键的列表的头部。如果键不存在,则在执行推送操作之前将其创建为空列表。(从左边插入)

template.opsForList().leftPush("list","java");
template.opsForList().leftPush("list","python");
template.opsForList().leftPush("list","c++");
返回的结果为推送操作后的列表的长度
1
2
3

Long leftPushAll(K key, V… values);
批量把一个数组插入到列表中

String[] strs = new String[]{"1","2","3"};
template.opsForList().leftPushAll("list",strs);
System.out.println(template.opsForList().range("list",0,-1));
[3, 2, 1]

Long rightPush(K key, V value);
将所有指定的值插入存储在键的列表的头部。如果键不存在,则在执行推送操作之前将其创建为空列表。(从右边插入)

template.opsForList().rightPush("listRight","java");
template.opsForList().rightPush("listRight","python");
template.opsForList().rightPush("listRight","c++");
1
2
3

Long rightPushAll(K key, V… values);

String[] strs = new String[]{"1","2","3"};
template.opsForList().rightPushAll("list",strs);
System.out.println(template.opsForList().range("list",0,-1));
[1, 2, 3]

void set(K key, long index, V value);
在列表中index的位置设置value值

System.out.println(template.opsForList().range("listRight",0,-1));
template.opsForList().set("listRight",1,"setValue");
System.out.println(template.opsForList().range("listRight",0,-1));
[java, python, oc, c++]
[java, setValue, oc, c++]

Long remove(K key, long count, Object value);
从存储在键中的列表中删除等于值的元素的第一个计数事件。
计数参数以下列方式影响操作:
count> 0:删除等于从头到尾移动的值的元素。
count <0:删除等于从尾到头移动的值的元素。
count = 0:删除等于value的所有元素。

System.out.println(template.opsForList().range("listRight",0,-1));
template.opsForList().remove("listRight",1,"setValue");//将删除列表中存储的列表中第一次次出现的“setValue”。
System.out.println(template.opsForList().range("listRight",0,-1));
[java, setValue, oc, c++]
[java, oc, c++]

V index(K key, long index);
根据下表获取列表中的值,下标是从0开始的

System.out.println(template.opsForList().range("listRight",0,-1));
System.out.println(template.opsForList().index("listRight",2));
[java, oc, c++]
c++

V leftPop(K key);
弹出最左边的元素,弹出之后该值在列表中将不复存在

System.out.println(template.opsForList().range("list",0,-1));
System.out.println(template.opsForList().leftPop("list"));
System.out.println(template.opsForList().range("list",0,-1));
[c++, python, oc, java, c#, c#]
c++
[python, oc, java, c#, c#]

V rightPop(K key);
弹出最右边的元素,弹出之后该值在列表中将不复存在

System.out.println(template.opsForList().range("list",0,-1));
System.out.println(template.opsForList().rightPop("list"));
System.out.println(template.opsForList().range("list",0,-1));
[python, oc, java, c#, c#]
c#
[python, oc, java, c#]

Redis的Hash数据结构

Long delete(H key, Object… hashKeys);
删除给定的哈希hashKeys

System.out.println(template.opsForHash().delete("redisHash","name"));
System.out.println(template.opsForHash().entries("redisHash"));
1
{class=6, age=28.1}

Boolean hasKey(H key, Object hashKey);
确定哈希hashKey是否存在

System.out.println(template.opsForHash().hasKey("redisHash","666"));
System.out.println(template.opsForHash().hasKey("redisHash","777"));
true
false

HV get(H key, Object hashKey);
从键中的哈希获取给定hashKey的值

System.out.println(template.opsForHash().get("redisHash","age"));
26

Set keys(H key);
获取key所对应的散列表的key

System.out.println(template.opsForHash().keys("redisHash"));
//redisHash所对应的散列表为{class=1, name=666, age=27}
[name, class, age]

Long size(H key);
获取key所对应的散列表的大小个数

System.out.println(template.opsForHash().size("redisHash"));
//redisHash所对应的散列表为{class=1, name=666, age=27}
3

void putAll(H key, Map<? extends HK, ? extends HV> m);
使用m中提供的多个散列字段设置到key对应的散列表中

Map<String,Object> testMap = new HashMap();
testMap.put("name","666");
testMap.put("age",27);
testMap.put("class","1");
template.opsForHash().putAll("redisHash1",testMap);
System.out.println(template.opsForHash().entries("redisHash1"));
{class=1, name=jack, age=27}

void put(H key, HK hashKey, HV value);
设置散列hashKey的值

template.opsForHash().put("redisHash","name","666");
template.opsForHash().put("redisHash","age",26);
template.opsForHash().put("redisHash","class","6");
System.out.println(template.opsForHash().entries("redisHash"));
{age=26, class=6, name=666}

List values(H key);
获取整个哈希存储的值根据密钥

System.out.println(template.opsForHash().values("redisHash"));
[tom, 26, 6]

Map<HK, HV> entries(H key);
获取整个哈希存储根据密钥

System.out.println(template.opsForHash().entries("redisHash"));
{age=26, class=6, name=tom}

Cursor<Map.Entry<HK, HV>> scan(H key, ScanOptions options);
使用Cursor在key的hash中迭代,相当于迭代器。

Cursor<Map.Entry<Object, Object>> curosr = template.opsForHash().scan("redisHash", 
  ScanOptions.ScanOptions.NONE);
    while(curosr.hasNext()){
        Map.Entry<Object, Object> entry = curosr.next();
        System.out.println(entry.getKey()+":"+entry.getValue());
    }
age:27
class:6
name:666

Redis的Set数据结构

Long add(K key, V… values);
无序集合中添加元素,返回添加个数
也可以直接在add里面添加多个值 如:template.opsForSet().add(“setTest”,“aaa”,“bbb”)

String[] strs= new String[]{"str1","str2"};
System.out.println(template.opsForSet().add("setTest", strs));
2

Long remove(K key, Object… values);
移除集合中一个或多个成员

String[] strs = new String[]{"str1","str2"};
System.out.println(template.opsForSet().remove("setTest",strs));
2

V pop(K key);
移除并返回集合中的一个随机元素

System.out.println(template.opsForSet().pop("setTest"));
System.out.println(template.opsForSet().members("setTest"));
bbb
[aaa, ccc]

Boolean move(K key, V value, K destKey);
将 member 元素从 source 集合移动到 destination 集合

template.opsForSet().move("setTest","aaa","setTest2");
System.out.println(template.opsForSet().members("setTest"));
System.out.println(template.opsForSet().members("setTest2"));
[ccc]
[aaa]

Long size(K key);
无序集合的大小长度

System.out.println(template.opsForSet().size("setTest"));
1

Set members(K key);
返回集合中的所有成员

System.out.println(template.opsForSet().members("setTest"));
[ddd, bbb, aaa, ccc]

Cursor scan(K key, ScanOptions options);
遍历set

Cursor<Object> curosr = template.opsForSet().scan("setTest", ScanOptions.NONE);
  while(curosr.hasNext()){
     System.out.println(curosr.next());
  }
ddd
bbb
aaa
ccc

Redis的ZSet数据结构

Boolean add(K key, V value, double score);
新增一个有序集合,存在的话为false,不存在的话为true


System.out.println(template.opsForZSet().add("zset1","zset-1",1.0));
true

Long add(K key, Set<TypedTuple> tuples);
新增一个有序集合

ZSetOperations.TypedTuple<Object> objectTypedTuple1 = new DefaultTypedTuple<>("zset-5",9.6);
ZSetOperations.TypedTuple<Object> objectTypedTuple2 = new DefaultTypedTuple<>("zset-6",9.9);
Set<ZSetOperations.TypedTuple<Object>> tuples = new HashSet<ZSetOperations.TypedTuple<Object>>();
tuples.add(objectTypedTuple1);
tuples.add(objectTypedTuple2);
System.out.println(template.opsForZSet().add("zset1",tuples));
System.out.println(template.opsForZSet().range("zset1",0,-1));
[zset-1, zset-2, zset-3, zset-4, zset-5, zset-6]

Long remove(K key, Object… values);
从有序集合中移除一个或者多个元素

System.out.println(template.opsForZSet().range("zset1",0,-1));
System.out.println(template.opsForZSet().remove("zset1","zset-6"));
System.out.println(template.opsForZSet().range("zset1",0,-1));
[zset-1, zset-2, zset-3, zset-4, zset-5, zset-6]
1
[zset-1, zset-2, zset-3, zset-4, zset-5]

Long rank(K key, Object o);
返回有序集中指定成员的排名,其中有序集成员按分数值递增(从小到大)顺序排列


System.out.println(template.opsForZSet().range("zset1",0,-1));
System.out.println(template.opsForZSet().rank("zset1","zset-2"));
[zset-2, zset-1, zset-3, zset-4, zset-5]

0 //表明排名第一
Set range(K key, long start, long end);
通过索引区间返回有序集合成指定区间内的成员,其中有序集成员按分数值递增(从小到大)顺序排列

System.out.println(template.opsForZSet().range("zset1",0,-1));
[zset-2, zset-1, zset-3, zset-4, zset-5]

Long count(K key, double min, double max);
通过分数返回有序集合指定区间内的成员个数

System.out.println(template.opsForZSet().rangeByScore("zset1",0,5));
System.out.println(template.opsForZSet().count("zset1",0,5));
[zset-2, zset-1, zset-3]
3

Long size(K key);
获取有序集合的成员数,内部调用的就是zCard方法

System.out.println(template.opsForZSet().size("zset1"));
6

Double score(K key, Object o);
获取指定成员的score值

System.out.println(template.opsForZSet().score("zset1","zset-1"));
2.2

Long removeRange(K key, long start, long end);
移除指定索引位置的成员,其中有序集成员按分数值递增(从小到大)顺序排列

System.out.println(template.opsForZSet().range("zset2",0,-1));
System.out.println(template.opsForZSet().removeRange("zset2",1,2));
System.out.println(template.opsForZSet().range("zset2",0,-1));
[zset-1, zset-2, zset-3, zset-4]
2
[zset-1, zset-4]

Cursor<TypedTuple> scan(K key, ScanOptions options);
遍历zset

Cursor<ZSetOperations.TypedTuple<Object>> cursor = template.opsForZSet().scan("zzset1", ScanOptions.NONE);
    while (cursor.hasNext()){
       ZSetOperations.TypedTuple<Object> item = cursor.next();
       System.out.println(item.getValue() + ":" + item.getScore());
    }
zset-1:1.0
zset-2:2.0
zset-3:3.0
zset-4:6.0

引用链接:https://lionli.blog.csdn.net/article/details/82011670?spm=1001.2014.3001.5506

设置过期时间:

 redisTemplate.opsForSet().getOperations().expire(key, 5, TimeUnit.HOURS);
 redisTemplate.opsForHash().getOperations().expire(key, 5, TimeUnit.HOURS);
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

爱上编程2705

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值