当前位置: 首页 > 编程笔记 >

如何在Redis中实现分页排序查询过程解析

宰父子安
2023-03-14
本文向大家介绍如何在Redis中实现分页排序查询过程解析,包括了如何在Redis中实现分页排序查询过程解析的使用技巧和注意事项,需要的朋友参考一下

Redis是一个高效的内存数据库,它支持包括String、List、Set、SortedSet和Hash等数据类型的存储,在Redis中通常根据数据的key查询其value值,Redis没有条件查询,在面对一些需要分页或排序的场景时(如评论,时间线),Redis就不太好不处理了。

前段时间在项目中需要将每个主题下的用户的评论组装好写入Redis中,每个主题会有一个topicId,每一条评论会和topicId关联起来,得到大致的数据模型如下:

{
  topicId: 'xxxxxxxx',
  comments: [
    {
      username: 'niuniu',
      createDate: 1447747334791,
      content: '在Redis中分页',
      commentId: 'xxxxxxx',
      reply: [
        {
          content: 'yyyyyy'
          username: 'niuniu'
        },
        ...
      ]
    },
    ...
  ]}

将评论数据从MySQL查询出来组装好存到Redis后,以后每次就可以从Redis获取组装好的评论数据,从上面的数据模型可以看出数据都是key-value型数据,无疑要采用hash进行存储,但是每次拿取评论数据时需要分页而且还要按createDate字段进行排序,hash肯定是不能做到分页和排序的。

那么,就挨个看一下Redis所支持的数据类型:

Hash

主要用于存储key-value型数据,评论模型中全是key-value型数据,所以在这里Hash无疑会用到。

List

主要用于存储一个列表,列表中的每一个元素按元素的插入时的顺序进行保存,如果我们将评论模型按createDate排好序后再插入List中,似乎就能做到排序了,而且再利用List中的LRANGE key start stop指令还能做到分页。嗯,到这里List似乎满足了我们分页和排序的要求,但是评论还会被删除,就需要更新Redis中的数据,如果每次删除评论后都将Redis中的数据全部重新写入一次,显然不够优雅,效率也会大打折扣,如果能删除指定的数据无疑会更好,而List中涉及到删除数据的就只有LPOP和RPOP这两条指令,但LPOP和RPOP只能删除列表头和列表尾的数据,不能删除指定位置的数据,所以List也不太适合。

Set

主要存储无序集合,无序!排除。

SortedSet

主要存储有序集合,SortedSet的添加元素指令ZADD key score member [[score,member]…]会给每个添加的元素member绑定一个用于排序的值score,SortedSet就会根据score值的大小对元素进行排序,在这里就可以将createDate当作score用于排序,SortedSet中的指令ZREVRANGE key start stop又可以返回指定区间内的成员,可以用来做分页,SortedSet的指令ZREM key member可以根据key移除指定的成员,能满足删评论的要求,所以,SortedSet在这里是最适合的。

所以,我需要用到的数据类型有SortSet和Hash,SortSet用于做分页排序,Hash用于存储具体的键值对数据,我画出了如下的结构图:


在上图的SortSet结构中将每个主题的topicId作为set的key,将与该主题关联的评论的createDate和commentId分别作为set的score和member,commentId的顺序就根据createDate的大小进行排列。 当需要查询某个主题某一页的评论时,就可主题的topicId通过指令zrevrange topicId (page-1)×10 (page-1)×10+perPage这样就能找出某个主题下某一页的按时间排好顺序的所有评论的commintId。page为查询第几页的页码,perPage为每页显示的条数。 当找到所有评论的commentId后,就可以把这些commentId作为key去Hash结构中去查询该条评论对应的内容。 这样就利用SortSet和Hash两种结构在Redis中达到了分页和排序的目的。

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持小牛知识库。

 类似资料:
  • 本文向大家介绍如何用java实现分页查询,包括了如何用java实现分页查询的使用技巧和注意事项,需要的朋友参考一下 1.基本思路 我现阶段的分页查询的实现是基于sql语句的。 构造出相应的a和b就可以查询出想要的数据,在显示在页面上。重点是要构造出当前的页数,就要封装一个javaBean,存储有关分页的基本属性。 这样只需在service层计算想要的页数,并封装基本的信息,在查询出来显示在前端就可

  • 本文向大家介绍JQuery+Ajax实现数据查询、排序和分页功能,包括了JQuery+Ajax实现数据查询、排序和分页功能的使用技巧和注意事项,需要的朋友参考一下 之前很少会用javascript去实现页功能主要怕麻烦,但了解JQuery后这种想法发生了变化;有了这样的脚本组件就可以在编写脚本时方便和HTML隔离出来,这样编写高重用性的脚本就更方便。下面就是介绍在学习JQuery过程中编写的基于A

  • 本文向大家介绍ajax实现分页和分页查询,包括了ajax实现分页和分页查询的使用技巧和注意事项,需要的朋友参考一下 之前有写过ajax的加载页面,是非常简单的,而且不需要重新刷新页面,写起来也是非常的方便,今天写的分页是不用封装page.class.php的,是单纯的js和ajax写出来的 首先为了页面的整齐与美观,我用到了bootstrap,需要引进所需要的文件包 下面是页面显示的内容 下面是j

  • 如何使用Graphql SPQR实现查询过滤器和排序? 我正在寻找一个解决方案,用Graphql SPQR的模式看起来像这样。

  • 我试图指定一个用注释的存储库方法和一个带有对象的Pagable: 编辑1:此存储库正在扩展分页和排序存储库。 对象使用以下方法签名指定: 但生成的输出查询没有排序选项,例如: ...在我期待的时候: 这里有人遇到过这样的问题吗?我使用的是Spring Boot 1.5。x。

  • 本文向大家介绍如何使用 Spring Boot 实现分页和排序?相关面试题,主要包含被问及如何使用 Spring Boot 实现分页和排序?时的应答技巧和注意事项,需要的朋友参考一下 使用 Spring Boot 实现分页非常简单。使用 Spring Data-JPA 可以实现将可分页的传递给存储库方法。