Redis 的 hash,及其序列化问题

  • 介绍
  • 常用命令
  • 应用场景
  • hash的序列化存储方式

介绍

一次应用中,需要将MySQL中的表在redis中缓存一份,防止查询次数太多,对数据库造成压力。用到了hash这种结构,对此进行一个理解。Redis hash数据结构 是一个键值对(key-value)集合,它是一个 string 类型的 fieldvalue 的映射表(它的key取名为field,为了和redis的key做区分),redis 本身就是一个 key-value 型数据库,因此 hash 数据结构相当于在 value 中又套了一层 key-value 型数据。所以 redis 中 hash 数据结构特别适合存储关系型对象。结构如下表示:

  • key : redis的key

    • field: hash的key

      • value: hash的value

结构虽然不是很难,用编程语言可以理解为Map<key, Map<field,value>>。但是它的作用可是很大。

常用命令

  • 单次操作命令:

hset “key” “field” value [field value]: 存放指定key的field和value值。
hget “key” “field” 获取存储在哈希表中指定字段的值。
hdel “key” “field1” “field2” 删除一个或多个哈希表字段
hexists “key” “field” 查看哈希表key中,指定的字段是否存在

  • 批量操作命令:

hgetall key 获取在哈希表中指定key的所有字段和值
hkeys key 获取所有哈希表中的字段(field)
hmget key field1 field2 获取所有给定字段的值
hmset key field1 value1 field2 value2 同时将多个field-value(域-值)对设置到哈希表key中
hvals key获取哈希表中所有的值(value)

因为是对关系型对象的存储,我们最常用的就是批量的操作,因为这样连接只用获取一次吗。同时,在JedisCluster下,有很多便于操作的方法,最常用的像hmset(可以直接填入一个map作为hash)、hgetAll(返回一个Map<String,String>类型)。。。。引用如下:

 @Testpublic void testHash() {Map<String,String> map = new HashMap<String,String>();map.put("key1","value1");map.put("key2","value2");map.put("key3","value3");map.put("key4","value4");jedis.hmset("hash",map);jedis.hset("hash", "key5", "value5");System.out.println("散列hash的所有键值对为:"+jedis.hgetAll("hash"));//return Map<String,String>System.out.println("散列hash的所有键为:"+jedis.hkeys("hash"));//return Set<String>System.out.println("散列hash的所有值为:"+jedis.hvals("hash"));//return List<String>System.out.println("将key6保存的值加上一个整数,如果key6不存在则添加key6:"+jedis.hincrBy("hash", "key6", 6));System.out.println("散列hash的所有键值对为:"+jedis.hgetAll("hash"));System.out.println("将key6保存的值加上一个整数,如果key6不存在则添加key6:"+jedis.hincrBy("hash", "key6", 3));System.out.println("散列hash的所有键值对为:"+jedis.hgetAll("hash"));System.out.println("删除一个或者多个键值对:"+jedis.hdel("hash", "key2"));System.out.println("散列hash的所有键值对为:"+jedis.hgetAll("hash"));System.out.println("散列hash中键值对的个数:"+jedis.hlen("hash"));System.out.println("判断hash中是否存在key2:"+jedis.hexists("hash","key2"));System.out.println("判断hash中是否存在key3:"+jedis.hexists("hash","key3"));System.out.println("获取hash中的值:"+jedis.hmget("hash","key3"));System.out.println("获取hash中的值:"+jedis.hmget("hash","key3","key4"));}

应用场景

上面我们讨论了hash可以存储关系型对象,MySQL的关系型数据缓存。接下来分析一下它的具体设计:
通常情况下,我们用redis的key来指定一种类型的对象,比如用户。

key可以设计为(redis_user),value就是user对象的映射了,但是这样相当于把整个用户都放到了一个节点key上,如果redis发生崩溃,造成的影响可不小。

换一种方式,我们把key设计为(redis_userId),这样虽然能占用多的key节点,假如用户是成千上万的,导致了每个用户占用一个key,这样使用hash的意义也就不大了。

所以我们使用hash结构,既要利用其特点,也要考虑redis集群状态下的节点分布问题。所以对key的设计是比较重要的,例如在key上加一个id对某个数取余的标志。让key分散开来,例如(redis_userId%10),因为放入的对象还是带着自己的id。操作也不会造成影响。

hash的序列化存储方式

通常情况,存入hash的对象需要对其序列化存储。因为普通的JSONString类型占用空间较大,而且序列化后方便了跨平台的传输和使用。常用的序列化方式有:
JdkSerializationRedisSerializer、OxmSerializer、StringRedisSerializer、==Kryo-Serializers ==这些序列化方式。我们此次用到的是Kryo方式。先看一下特点:

Kryo 是一个快速序列化/反序列化工具,其使用了字节码生成机制(底层依赖了 ASM 库),因此具有比较好的运行速度。

Kryo 序列化出来的结果,是其自定义的、独有的一种格式,不再是 JSON 或者其他现有的通用格式;而且,其序列化出来的结果是二进制的(即 byte[];而 JSON 本质上是字符串 String);二进制数据显然体积更小,序列化、反序列化时的速度也更快。

Kryo 一般只用来进行序列化(然后作为缓存,或者落地到存储设备之中)、反序列化,而不用于在多个系统、甚至多种语言间进行数据交换 —— 目前 kryo 也只有 java 实现。

像 Redis 这样的存储工具,是可以安全地存储二进制数据的,所以可以直接把 Kryo 序列化出来的数据存进去。

具体的使用我们参考一下大佬写的:kryo使用

Redis 的 hash,及其序列化问题相关推荐

  1. redis的hash操作在集中式session中的应用

    在集群部署时,为了高可用性的目的,往往把session进行共享,共享分为两种:session复制和集中式管理. redis在session集中式管理中可以起到比较大的作用. 制约session集中式共 ...

  2. redis数据结构hash

    Redis数据结构之hash Hash存储结构 Hash是一个string 类型的field和value的映射表.Hash特别适合存储对象,相对于将对象的每个字段存成单个string 类型.一个对象存 ...

  3. Redis数据结构Hash应用场景-存储商品、购物车、淘宝短链接、分布式Session、用户注册、发微博功能

    Hash应用场景 Hash Hash应用场景 redis存储java对象常用String,那为什么还要用hash来存储? SpringBoot+redis+hash存储商品数据 短链接 场景1:淘宝短 ...

  4. redis 中 Hash哈希介绍 及常用命令 (附有示例)

    目录 一.Redis中Hash介绍 二.常用命令 三.示例 hset hget hmset   .. hexists hkeys hvals hincrbu hsetnx 四.redis中Hash底层 ...

  5. 【springboot进阶】springboot集成fastjson(三)配置redis使用fastJson进行序列化

    目录 一.引入依赖 二.添加redis连接配置 三.新建RedisConfig类配置 四.测试 五.踩过的坑 数字型的保存 对象的保存 上一章节,我们说到fastjson的自定义序列化和反序列化,这章 ...

  6. Redis问题总结(序列化事务集群)

    Redis简介 简单介绍 Redis:开源.免费.非关系型数据库.K-V数据库.内存数据库,支持持久化.事务和备份,集群(支持16个库)等高可用功能.并且性能极高(可以达到100000+的QPS),易 ...

  7. Redis之Hash数据结构

    0.前言 redis是KV型的内存数据库, 数据库存储的核心就是Hash表, 我们执行select命令选择一个存储的db之后, 所有的操作都是以hash表为基础的, 下面会分析下redis的hash数 ...

  8. redis java序列化_java处理redis的几种序列化策略

    简单记录一下java处理redis的几种序列化策略,这里使用的环境是springboot 2.0.4 springboot中提供了StringRedisTemplate和RedisTemplate两种 ...

  9. Redis之Hash超详细API使用及应用场景介绍,不看亏了!

    j3_liuliang Redis常用API即应用场景系列(Hash),如果觉得有用可以关注博主,不定时更新哦! 相关文章导航 超详细Redis之Key操作API,什么?看不懂!你来锤我 Redis之 ...

最新文章

  1. CentOS 6下编译安装Nginx
  2. STM32 CAN 过滤器、滤波屏蔽器配置总结
  3. 【IntelliJ IDEA】添加一个新的tomcat,tomcat启动无法访问欢迎页面,空白页,404
  4. 60TB 数据量的作业从 Hive 迁移到 Spark 在 Facebook 的实践
  5. else应输入一个语句是什么意思_Python学习基础篇 -4: Python中的转弯---分支语句
  6. ufei pe安装linux,制作UEFI(64位)下的WinPE + Ubuntu + Acronis多启动U盘
  7. new hashmap 初始大小_你们要的HashMap工作原理!它来了!!!
  8. paper reading:高光谱遥感影像空谱特征提取与分类方法研究 - 康旭东
  9. 唯有自己变得强大_强大自己!(经典)
  10. 乐高ev3搭建图纸大全_乐高课程的详细介绍,内附7岁系列课程,还不抓紧时间收藏...
  11. 基于OP放大器的有源模拟滤波器设计--一阶有源滤波器
  12. 【EMC电磁兼容】01.12——差模与共模
  13. CI/CD——构建企业级Docker+Jenkins+Git+Harbor流水线自动化持续集成持续发布平台
  14. Codeforces Round #439 (Div. 2) E. The Untended Antiquity (hash+数状数组)
  15. List逆向遍历、反向遍历--Iterator详解
  16. OSPF多区原理与配置
  17. 解决this application failed to start
  18. 计蒜客 最后一个单词的长度
  19. 全志D1-H裸奔工具XFEL
  20. 外盘期货策略|9月17日美原油期货日内操盘策略

热门文章

  1. virtio虚拟化框架
  2. t20天正插件5.0怎么安装
  3. linux上oracle导入mysql_Linux 下 oracle 导入数据库—数据泵方式导入dmp文件
  4. RPC实现和原理解析
  5. 服务器品牌有哪些?如何选择服务器?主要有哪些参数?
  6. 12306订票助手.NET
  7. 【线性代数】结合 Ax=b 的通解结构,直观理解秩、线性变换、相关无关、基础解系
  8. vue移动助手实践(一)——基于vue的换肤功能
  9. 栈(stack) C语言实现 详解
  10. 使用ps制作账号管理页面