1、Redis的简介

Redis中文官网链接:

1.1、NoSql

  1. NoSql 是Not-Only Sql的简写,泛指非关系型数据库
  2. 关系型数据库不太适合存储非结构化的大数据(现在的非结构化的数据占比90%),所以提出了一个新的数据库解决方案,来存储这样的数据。
  3. NoSql的分类
    • 键值对模型的NoSQL:Tokyo、Cabinet/Tyrant、Redis、Voldemort、Berkeley DB
      应用场景:内容缓存,主要用于处理大量数据的高访问负载
      优势:快速查询
      劣势:存储的数据缺少结构化
    • 列式模型的NoSQL:Cassandra, HBase, Riak
      应用场景:分布式的文件系统
      优势:查找速度快,可扩展性强,更容易进行分布式扩展
      劣势:功能相对局限
    • 文档模型的NoSQL:CouchDB、MongoDB
      应用场景:Web应用
      优势:数据结构要求不严格
      劣势:查询性能不高,而且缺乏统一的查询语法
    • 图模型的NoSQL:Neo4J、InfoGrid、Infinite Graph
      应用场景:社交网络
      优势:利用图结构相关算法。
      劣势:需要对整个图做计算才能得出结果,不容易做分布式的集群方案。

1.2、Redis

Redis是C语言开发的一个开源的高性能(基于内存)的k-v键值对的NO-SQL数据库,提供了丰富的数据类型。

  • 字符串类型

  • 散列类型(hash)

  • 列表类型(list)

  • 集合类型(set)

  • 有序集合类型(sortedSet)

1.3、Redis的发展史

2008年,意大利的一家创业公司Merzia推出了一款基于MySQL的网站实时统计系统LLOOGG,然而没过多久该公司的创始人 Salvatore Sanfilippo便对MySQL的性能感到失望,于是他决定亲自为LLOOGG量身定做一个数据库,并于2009年开发完成,这个数据库就是Redis。不过Salvatore Sanfilippo并不满足只将Redis用于LLOOGG这一款产品,而是希望更多的人使用它,于是在同一年Salvatore Sanfilippo将Redis开源发布,并开始和Redis的另一名主要的代码贡献者Pieter Noordhuis一起继续着Redis的开发,直到今天。

SalvatoreSanfilippo自己也没有想到,短短的几年时间,Redis就拥有了庞大的用户群体。Hacker News在2012年发布了一份数据库的使用情况调查,结果显示有近12%的公司在使用Redis。国内如新浪微博、街旁网、知乎网,国外如GitHub、Stack Overflow、Flickr等都是Redis的用户。

VMware公司从2010年开始赞助Redis的开发,Salvatore Sanfilippo和Pieter Noordhuis也分别在3月和5月加入VMware,全职开发Redis。

1.4、Redis的应用场景

缓存(数据查询、短连接、新闻内容、商品内容等等)。(最多使用)

分布式集群架构中的session分离。

聊天室的在线好友列表。

任务队列。(秒杀、抢购、12306等等)

应用排行榜。

网站访问统计。

数据过期处理(可以精确到毫秒)

1.5、Redis的特点

redis数据访问速度快(数据在内存中)

redis有数据持久化机制(持久化机制有两种:1、定期将内存数据dump到磁盘;2、aof(append only file)持久化机制——用记日志的方式记录每一条数据更新操作,一旦出现灾难事件,可以通过日志重放来恢复整个数据库)

redis支持集群模式(容量可以线性扩展)

redis相比其他缓存工具(ehcache/memcached),有一个鲜明的优势:支持丰富的数据结构

2、Redis集群的搭建

2.1、下载

官网地址:https://redis.io/

下载地址:http://download.redis.io/releases/redis-4.0.14.tar.gz

2.2、​​​​​​​安装环境

Redis安装一般会在Linux系统下进行安装,又因为redis是使用c语言开发,所以需要c语言环境。

Linux:centOS7.7

VMware:14

C语言环境:yum install gcc-c++

2.3、安装步骤

1、上传、解压、更名

2、进入redis执行make命令编译源码

3、安装Redis

make install PREFIX=/usr/local/redis

成功之后可以在指定的目录下生成bin目录

4、配置环境变量

#redis env
export REDIS_HOME=/usr/local/redis
export PATH=$REDIS_HOME/bin:$PATH

5、帮助

redis-cli --help

2.4、Redis的启动

分为前台启动和后台启动

2.4.1前台启动

#启动
redis-server
#关闭
ctrl+C

2.4.2、后台启动

注意: 后台启动需要将解压出来的目录中的redis.conf文件复制到bin目录下,并且修改redis.conf中的dameonize参数为yes(应该在136行)

#启动
redis-server /usr/local/redis/bin/redis.conf
#关闭
redis-cli shutdown

2.3、客户端连接

redis-cli
# 下面是在客户端界面下的一些基础操作
127.0.0.1:6379> set user1 gaoyuanyuan        <= 设置一个键值对
OK
127.0.0.1:6379> set user2 linzhiling     <= 设置一个键值对
OK
127.0.0.1:6379> get user1                    <= 获取键user1的value
"gaoyuanyuan"
127.0.0.1:6379> get user2                    <= 获取键user2的value
"linzhiling"
127.0.0.1:6379> keys *                       <= 查看所有的key
1) "user1"
2) "user2"

可以给server设置密码,主机名,端口,设置之后客户端想要连接server就要输入主机名,端口,密码(在redis.conf中设置)

#设置了主机名,端口,密码
#开启服务端还是redis-server redis-server /usr/local/redis/bin/redis.conf
#关闭服务端
redis-cli -h node01 -a 123123
#客户端连接
redis-cli -h node01 -p 6379 -a 123123

2.4、使用jedis连接客户端

Redis不仅是使用命令来操作,现在基本上主流的语言都有客户端支持,比如java、C、C#、C++、php、Node.js、Go等。

在官方网站里列一些Java的客户端,有Jedis、Redisson、Jredis、JDBC-Redis、等其中官方推荐使用Jedis和Redisson。 在企业中用的最多的就是Jedis,下面我们就重点学习下Jedis。

Jedis同样也是托管在github上,地址:httpsRedis.assets//github.com/xetorthio/jedis

2.4.1、单线程连接

package Day01/*** 单线程连接*/import redis.clients.jedis.Jedisobject _01JedisDemo {def main(args: Array[String]): Unit = {//使用jedis,创建一个redis对象val jedis = new Jedis("node01", 6379)//进行密码验证,如果没有设置密码跳过jedis.auth("123123")//设置键值对,成功返回OKjedis.set("name","张作霖")//追加,如果key存在就覆盖,不存在就追加到其他kv后面jedis.append("age","22")//通过k获取vprintln(jedis.get("name"),jedis.get("age"))}
}

2.4.2、线程池连接

package Day01import java.utilimport redis.clients.jedis.{Jedis, JedisPool}/*** 连接池连接*/
object _02JedisPoolDemo {def main(args: Array[String]): Unit = {//获取jedis的连接池对象val pool = new JedisPool("node01", 6379)//从连接池中获取一个具体的连接 对象val jedis: Jedis = pool.getResource//进行密码验证,如果没有设置密码跳过jedis.auth("123123")//设置一个kvjedis.set("gender","男")jedis.mset("hobby","women","aa","sun")//获取val hobby: util.List[String] = jedis.mget("hobby","aa")//输出println(hobby)}
}

3、Redis的数据类型

3.1、字符串类型

3.1.1、命令行操作

#创建一个kv
node01:6379> set name mark
OK
#获取一个k对应的v
node01:6379> get name
"mark"
#创建多个kv
node01:6379> mset name mary age 23 gender f
OK
#获取多个k的v
node01:6379> mget name age gender
1) "mary"
2) "23"
3) "f"
node01:6379> set num 1
OK
#使num自增1(v必须使数字)
node01:6379> incr num
(integer) 2
node01:6379> get num
"2"
#使num自减1(v必须使数字)
node01:6379> decr num
(integer) 1
node01:6379> get num
"1"
#使num自增2(v必须使数字)
node01:6379> incrby num 2
(integer) 3
node01:6379> get num
"3"
#使num自减1(v必须使数字)
node01:6379> decrby num 2
(integer) 1
node01:6379> get num
"1"

3.1.2、jedis操作(scala/java都行)

package Day01import java.utilimport org.apache.commons.pool2.impl.GenericObjectPoolConfig
import redis.clients.jedis.{Jedis, JedisPool}/*** 连接池连接*/
object _03StringTypeDemo {def main(args: Array[String]): Unit = {//连接池配置val config = new GenericObjectPoolConfigconfig.setMaxIdle(5)   //最大空闲线程数config.setMinIdle(2)   //最小空闲数config.setMaxTotal(10)   //线程总数//获取jedis的连接池对象val pool = new JedisPool(config,"node01", 6379,10000,"123123")//从连接池中获取一个具体的连接 对象val jedis: Jedis = pool.getResource//设置一个kvjedis.set("name","mark")//设置多个kvjedis.mset("age","21","gender","m")//自增1jedis.incr("age")//自减1jedis.decr("age")//自增2jedis.incrBy("age",2)//获取val hobby: util.List[String] = jedis.mget("name","age","gender")//输出println(hobby)//将线程归还给线程池jedis.close()}
}

3.2、Hash类型

Redis hash 是一个 string 类型的 field(字段) 和 value(值) 的映射表,hash 特别适合用于存储对象。
结构:key field value

3.2.1、命令行操作

node01:6379> hset mark age 23
(integer) 1node01:6379> hget mark age
"23"node01:6379> hset mark age 23 gender m
(integer) 1node01:6379> hmget mark age gender
1) "23"
2) "m"#没有hincr,只有hincrby
node01:6379> hincr mark age
(error) ERR unknown command `hincr`, with args beginning with: `mark`, `age`,node01:6379> hincrby mark age 2
(integer) 25#没有hdecrby
node01:6379> hdecrby mark age 2
(error) ERR unknown command `hdecrby`, with args beginning with: `mark`, `age`, `2`,node01:6379> hdel mark age
(integer) 1
node01:6379> hget mark age
(nil)#不能直接删k
node01:6379> hdel mark
(error) ERR wrong number of arguments for 'hdel' commandnode01:6379> hget mark gender
"m"
node01:6379> hdel mark gender
(integer) 1
node01:6379> hget mark gender
(nil)node01:6379> hmset ss aa 1 bb 2 cc 3
OKnode01:6379> hmget ss aa bb cc
1) "1"
2) "2"
3) "3"
node01:6379> hkeys ss
1) "aa"
2) "bb"
3) "cc"node01:6379> hvals ss
1) "1"
2) "2"
3) "3"

3.2.2、jedis操作

package Day01import java.utilimport redis.clients.jedis.{Jedis, JedisPool}import scala.collection.mutableobject _04HashTypeDemo {def main(args: Array[String]): Unit = {//获取jedis的连接池对象val pool = new JedisPool("qianfeng01", 6379)//从连接池中获取一个具体的连接 对象val jedis: Jedis = pool.getResource//设置一个购物车信息jedis.hset("xiaoming:shoppingcart","fruit","apple")jedis.hset("xiaoming:shoppingcart","T恤","200")//创建一个mapval map = new util.HashMap[String, String]()map.put("computer","lenovo")map.put("wanju","aotuman")//参数可以是mapjedis.hset("xiaoming:shoppingcart",map)//批量增加jedis.hmset("xiaoming:shoppingcart",map)//获取一条jedis.hget("xiaoming:shoppingcart","computer")//获取多条jedis.hmget("xiaoming:shoppingcart","fruit","computer","wanju")//删除jedis.hdel("xiaoming:shoppingcart","computer","fruit")//自增jedis.hincrBy("xiaoming:shoppingcart","T恤",50)//判断字段是否存在jedis.hexists("xiaoming:shoppingcart","computer")//字段存在不作任何操作,不存在则和hset一样jedis.hsetnx("xiaoming:shoppingcart","computer","hasee")//只获取字段名jedis.hkeys("xiaoming:shoppingcart")//只获取字段值jedis.hvals("xiaoming:shoppingcart")//获取字段数量jedis.hlen("xiaoming:shoppingcart")}
}

3.3、list类型

List是有序可重复的集合

ArrayList与LinkedList的区别

​ ArrayList使用数组方式存储数据,所以根据索引查询数据速度快,而新增或者删除元素时需要设计到位移操作,所以比较慢。

​ LinkedList使用双向链接方式存储数据,每个元素都记录前后元素的指针,所以插入、删除数据时只是更改前后元素的指针指向即可,速度非常快,然后通过下标查询元素时需要从头开始索引,所以比较慢,但是如果查询前几个元素或后几个元素速度比较快。

总结

arrayList在进行增删改时很麻烦

linkedList则无该问题,redis的list类型存储时采用linkedlist

redis存储list类型可以实现队列和堆栈,队列是先进先出,而堆栈是先进后出。

3.3.1、命令行操作

  • 从左边存值(堆栈)
  129.0.0.1Redis.assets6379> lpush list1 1 2 3 4 5 6(integer) 6
  • 从右边存值(队列)
  129.0.0.1Redis.assets6379> rpush list1 a b c d(integer) 10
  • 查看List值
  129.0.0.1Redis.assets6379> lrange list1 0 31) "6"2) "5"3) "4"4) "3"

如果查看全部,使用以下命令:

  129.0.0.1Redis.assets6379> lrange list1 0 -11) "6"2) "5"3) "4"4) "3"5) "2"6) "1"7) "a"8) "b"9) "c"10) "d"
  • 从两端弹出值
  129.0.0.1Redis.assets6379> lpush list1 1 2 3 4 5 6(integer) 6129.0.0.1Redis.assets6379> lrange list1 0 -11) "6"2) "5"3) "4"4) "3"5) "2"6) "1"129.0.0.1Redis.assets6379> lpop list1 "6"129.0.0.1Redis.assets6379> lrange list1 0 -11) "5"2) "4"3) "3"4) "2"5) "1"129.0.0.1Redis.assets6379> rpop list1"1"129.0.0.1Redis.assets6379> lrange list1 0 -11) "5"2) "4"3) "3"4) "2"
  • 获取列表的长度
  129.0.0.1Redis.assets6379> llen list1(integer) 4

其他命令

  • 删除列表中指定的值

    LREM key count value

    LREM命令会删除列表中前count个值为value的元素,返回实际删除的元素个数。根据count值的不同,该命令的执行方式会有所不同:

    当count>0时, LREM会从列表左边开始删除。

    当count<0时, LREM会从列表后边开始删除。

    当count=0时,LREM删除所有值为value的元素。

  • 获得/设置指定索引的元素值

    LINDEX key index

    LSET key index value

129.0.0.1Redis.assets6379> lindex lRedis.assetslist 2"1"129.0.0.1Redis.assets6379> lset lRedis.assetslist 2 2OK129.0.0.1Redis.assets6379> lrange lRedis.assetslist 0 -11) "6"2) "5"3) "2"4) "2"
  • 只保留列表指定片段,指定范围和LRANGE一致

    LTRIM key start stop

  129.0.0.1Redis.assets6379> lrange lRedis.assetslist 0 -11) "6"2) "5"3) "0"4) "2"129.0.0.1Redis.assets6379> ltrim lRedis.assetslist 0 2OK129.0.0.1Redis.assets6379> lrange lRedis.assetslist 0 -11) "6"2) "5"3) "0"
  • 向列表中插入元素

    LINSERT key BEFORE|AFTER pivot value

    该命令首先会在列表中从左到右查找值为pivot的元素,然后根据第二个参数是BEFORE还是AFTER来决定将value插入到该元素的前面还是后面。

  129.0.0.1Redis.assets6379> lrange list 0 -11) "3"2) "2"3) "1"129.0.0.1Redis.assets6379> linsert list after 3 4(integer) 4129.0.0.1Redis.assets6379> lrange list 0 -11) "3"2) "4"3) "2"4) "1"
  • 将元素从一个列表转移到另一个列表中

    RPOPLPUSH source destination

  129.0.0.1Redis.assets6379> rpoplpush list newlist "1"129.0.0.1Redis.assets6379> lrange newlist 0 -11) "1"129.0.0.1Redis.assets6379> lrange list 0 -11) "3"2) "4"3) "2"

3.3.2、jedis操作(java版本)

import redis.clients.jedis.Jedis;
import java.util.Random;
import java.util.UUID;public class TaskProducer {private static Jedis jedis = new Jedis("node02", 6379);public static void main(String[] args) throws Exception {Random r = new Random();while (true) {int nextInt = r.nextInt(1000);Thread.sleep(2000 + nextInt);String taskId = UUID.randomUUID().toString();jedis.lpush("task-queue1", taskId);System.out.println("生成一条任务信息:" + taskId);}}
}
import redis.clients.jedis.Jedis;
import java.util.Random;public class TaskConsumer {private static Jedis jedis = new Jedis("node02", 6379);public static void main(String[] args) throws Exception {Random r = new Random();while (true) {Thread.sleep(2000);// 从task-queue1任务队列里取出一个任务,放到暂存队列里String taskId = jedis.rpoplpush("task-queue1", "temp-queue1");// 模拟处理任务if (r.nextInt(19) % 9 == 0) {// 任务处理失败,需要把任务信息从暂存队列里弹出来再放到任务队列里等待继续消费jedis.rpoplpush("temp-queue1", "task-queue1");System.out.println("任务处理失败:" + taskId);} else {jedis.rpop("temp-queue1");System.out.println("任务处理成功:" + taskId);}}}
}

3.4、set类型

Set类型的数据是有序且不可重复。

3.4.1、命令行操作

  • 添加元素
  129.0.0.1Redis.assets6379> sadd set1 1 2 3 3 4 5 5(integer) 5
  • 删除元素
  129.0.0.1Redis.assets6379> sadd set1 1 2 3 3 4 5 5(integer) 5129.0.0.1Redis.assets6379> srem set1 3(integer) 1129.0.0.1Redis.assets6379> smembers set11) "1"2) "2"3) "4"4) "5"
  • 查看元素
  129.0.0.1Redis.assets6379> smembers set11) "1"2) "2"3) "4"4) "5"
  • 判断元素是否存在
  129.0.0.1Redis.assets6379> sismember set1 6(integer) 0

运算命令

  • 差集运算
  129.0.0.1Redis.assets6379> sadd set3 2 3 4(integer) 3129.0.0.1Redis.assets6379> sadd set4 1 2 3(integer) 3129.0.0.1Redis.assets6379> sdiff set4 set31) "1"129.0.0.1Redis.assets6379> sdiff set3 set41) "4"
  • 交集运算
  129.0.0.1Redis.assets6379> sinter set3 set41) "2"2) "3"
  • 并集运算
  129.0.0.1Redis.assets6379> sunion set3 set41) "1"2) "2"3) "3"4) "4"

其他命令

  • 获得集合中元素的个数

    SCARD key

  129.0.0.1Redis.assets6379> smembers setA 1) "1"2) "2"3) "3"129.0.0.1Redis.assets6379> scard setA (integer) 3
  • 从集合中弹出一个元素

    SPOP key

  129.0.0.1Redis.assets6379> spop setA "1“

注意:由于集合是无序的,所有SPOP命令会从集合中随机选择一个元素弹出

3.4.2、jedis操作


import java.utilimport redis.clients.jedis.Jedisobject _06SetTypeDemo {def main(args: Array[String]): Unit = {//使用java的redis客户端API jedis, 要连接linux上的redis服务,主要要修改redis.conf下的bind为主机名或者而是Ipval jedis = new Jedis("node01", 6379)jedis.auth("123456")jedis.sadd("heros","superman","盖伦","daomei","毕加索")//获取val strings: util.Set[String] = jedis.smembers("heros")import  scala.collection.JavaConversions._for(i<- strings){println(i)}//删除 刀妹println(jedis.srem("heros", "daomei"))println("-----------删除后--------")for(i<- jedis.smembers("heros")){println(i)}//释放资源jedis.close()}
}

3.5、sortedSet类型

zset在设置时,会给设置一个分数,通过分数,可以进行排序。

3.5.1、命令行操作

  • 添加元素
  129.0.0.1Redis.assets6379> zadd zset1 1 haha 2 hehe 0 heihei(integer) 3
  • 删除元素
  129.0.0.1Redis.assets6379> zrem zset1 haha(integer) 1
  • 获得排名在某个范围的元素列表
  129.0.0.1Redis.assets6379> zrange zset1 0 31) "heihei"2) "hehe"129.0.0.1Redis.assets6379> zrevrange zset1 0 31) "hehe"2) "heihei"129.0.0.1Redis.assets6379> zrevrange zset1 0 3 withscores1) "hehe"2) "2"3) "heihei"4) "0"

其他命令

  • 获得指定分数范围的元素

    ZRANGEBYSCORE key min max [WITHSCORES]
    [LIMIT offset count]

  129.0.0.1Redis.assets6379> ZRANGEBYSCORE scoreboard 90 97 WITHSCORES1) "wangwu"2) "94"3) "lisi"4) "97"129.0.0.1Redis.assets6379> ZRANGEBYSCORE scoreboard 70 100 limit 1 21) "wangwu"2) "lisi"
  • 增加某个元素的分数,返回值是更改后的分数。

    ZINCRBY key increment member

  129.0.0.1Redis.assets6379> ZINCRBY scoreboard  4 lisi "101“
  • 获得集合中元素的数量

    ZCARD key

  129.0.0.1Redis.assets6379> ZCARD scoreboard(integer) 3
  • 获得指定分数范围内的元素个数

    ZCOUNT key min max

  129.0.0.1Redis.assets6379> ZCOUNT scoreboard 80 90(integer) 1
  • 按照排名范围删除元素

    ZREMRANGEBYRANK key start stop

  129.0.0.1Redis.assets6379> ZREMRANGEBYRANK scoreboard 0 1(integer) 2 129.0.0.1Redis.assets6379> ZRANGE scoreboard 0 -11) "lisi"
  • 按照分数范围删除元素

    ZREMRANGEBYSCORE key min max

  129.0.0.1Redis.assets6379> zadd scoreboard 84 zhangsan  (integer) 1129.0.0.1Redis.assets6379> ZREMRANGEBYSCORE scoreboard 80 100(integer) 1
  • 获取元素的排名

    从小到大

    ZRANK key member

  129.0.0.1Redis.assets6379> ZRANK scoreboard lisi (integer) 0

从大到小

ZREVRANK key member

  129.0.0.1Redis.assets6379> ZREVRANK scoreboard zhangsan (integer) 1

应用:商品销售排行榜

根据商品销售量对商品进行排行显示,定义sorted set集合,商品销售量为元素的分数。

定义商品销售排行榜key:itemsRedis.assetssellsort

写入商品销售量:

商品编号1001的销量是9,商品编号1002的销量是10

192.168.101.3Redis.assets7007> ZADD itemsRedis.assetssellsort 9 1001 10 1002

商品编号1001的销量加1

192.168.101.3Redis.assets7001> ZINCRBY itemsRedis.assetssellsort 1 1001

商品销量前10名:

192.168.101.3Redis.assets7001>  zrevrange zset1 0 9 withscores

3.5.2、jedis操作

scala

import java.utilimport redis.clients.jedis.{Jedis, Tuple}object _07SortedSetTypeDemo {def main(args: Array[String]): Unit = {//使用java的redis客户端API jedis, 要连接linux上的redis服务,主要要修改redis.conf下的bind为主机名或者而是Ipval jedis = new Jedis("node01", 6379)jedis.auth("123456")//添加几个商品销售量,销售量作为分数jedis.zadd("rank",100,"毛衣1")jedis.zadd("rank",110,"毛衣2")jedis.zadd("rank",90,"毛衣3")jedis.zadd("rank",120,"毛衣4")jedis.zadd("rank",100,"毛衣5")jedis.zadd("rank",80,"毛衣6")jedis.zadd("rank",70,"毛衣7")jedis.zadd("rank",88,"毛衣8")jedis.zadd("rank",50,"毛衣9")jedis.zadd("rank",200,"毛衣10")jedis.zadd("rank",250,"毛衣11")//获取销售量的前10名import scala.collection.JavaConversions._val strings: util.Set[String] = jedis.zrevrange("rank", 0, 9)for(i<-strings){println(i)}///获取销售量的前10名,并显示分数值(销售量)val tuples: util.Set[Tuple] = jedis.zrevrangeWithScores("rank",0,9)for(i<-tuples){println(i)}jedis.close()}
}

java1、

import redis.clients.jedis.Jedis;
import java.util.Random;public class LolBoxPlayer {private static Jedis jedis = new Jedis("node02", 6379);public static void main(String[] args) throws Exception {Random r = new Random();String[] heros = {"盖伦","轮子妈","蒙多","亚索","木木","刀妹","提莫","炼金"};while (true) {int index = r.nextInt(heros.length);String hero = heros[index];Thread.sleep(500);// 给英雄每次出场的分数加1,如果初次出场,zincrby方法会自动创建jedis.zincrby("hero:ccl", 1, hero);System.out.println(hero + "出场了");}}
}

java2、

import redis.clients.jedis.Jedis;
import redis.clients.jedis.Tuple;
import java.util.Set;public class LolBoxViewer {private static Jedis jedis = new Jedis("node02", 6379);public static void main(String[] args) throws Exception {// 计数器int i = 1;while (true) {Thread.sleep(3000);System.out.println("第" + i + "次查看榜单");// 从redis获取榜单排名信息,取5名Set<Tuple> heros = jedis.zrevrangeWithScores("hero:ccl", 0, 4);for (Tuple hero: heros) {System.out.println(hero.getElement() + "---------------" + hero.getScore());}i ++;System.out.println("");}}
}

Redis -- 01 【简介,特点,搭建,shell,数据类型】相关推荐

  1. 【重难点】【Redis 01】为什么使用 Redis、Redis 的线程模型、Redis 的数据类型及其底层数据结构

    [重难点][Redis 01]为什么使用 Redis.Redis 的线程模型.Redis 的数据类型及其底层数据结构 文章目录 [重难点][Redis 01]为什么使用 Redis.Redis 的线程 ...

  2. 【黑马程序员】Redis学习笔记001:Redis简介+五种基本数据类型

    一.Redis入门简介及基本操作命令 问题的抛出 出现的问题: 海量用户 高并发 罪魁祸首--关系型数据库: 性能瓶颈:磁盘IO性能低下 扩展瓶颈:数据关系复杂,扩展性差,不便于大规模集群 解决思路 ...

  3. 深入剖析Redis系列(三) - Redis集群模式搭建与原理详解

    前言 在 Redis 3.0 之前,使用 哨兵(sentinel)机制来监控各个节点之间的状态.Redis Cluster 是 Redis 的 分布式解决方案,在 3.0 版本正式推出,有效地解决了 ...

  4. Redis集群的搭建(具体步骤)

    Redis集群搭建 Redis的单机版安装:https://blog.csdn.net/qq_43412289/article/details/99815373 Redis的window版安装:htt ...

  5. Redis集群环境搭建实践

    本文是Redis集群学习的实践总结(基于Redis 6.0+),详细介绍逐步搭建Redis集群环境的过程,并完成集群伸缩的实践. Redis集群简介 Redis集群(Redis Cluster) 是R ...

  6. 2W 字详解 Redis 集群环境搭建实践

    点击上方 "终端研发部"关注, 星标或置顶一起成长 本文是Redis集群学习的实践总结(基于Redis 6.0+),详细介绍逐步搭建Redis集群环境的过程,并完成集群伸缩的实践. ...

  7. 第一章 Redis基础(简介+下载和安装+基本操作)----黑马

    第一章 Redis基础(简介+下载和安装+基本操作) ----黑马 文章目录 第一章 Redis基础(简介+下载和安装+基本操作) ----黑马 学习目标: 1. Redis 简介 1.1 NoSQL ...

  8. Redis集群架构搭建详解

    一.简介 这其实是一种分布式数据库,就是通过分片的机制储存数据,cluster中的每个节点仅仅储存数据哭的一部分数据,本质上就是实现数据库分片. 这种集群是一种去中心化的集群,也就是说,集群中的每个节 ...

  9. 《Redis实战》一1.2 Redis数据结构简介

    本节书摘来异步社区<Redis实战>一书中的第1章,第1.2节,作者: [美]Josiah L. Carlson(约西亚 L.卡尔森)译者: 黄健宏 责编: 杨海玲,更多章节内容可以访问云 ...

最新文章

  1. 支付宝支付 第二集:傻瓜式教程->获取支付的RSA公钥和私钥
  2. JavaScript学习笔记之数组(二)
  3. CH0103最短Hamilton路径 poj2288 Islands and Brigdes【状压DP】
  4. CSDN移动博文集锦之Android核心分析 (Z)
  5. ABP Framework 研习社经验总结(6.28-7.2)
  6. 谈谈我对MYSQL乱码的解决办法
  7. CentOS上安装mysql5.5.23
  8. 怎样下载python模块sublime text3中_python安装环境配置、python模块添加、sublime text编辑器配置...
  9. 面试问题_教资面试,结构化面试问题分享
  10. 设计模式のFactoryPattern(工厂模式)----创建模式
  11. 创建两个Thread子类,第一个用run()方法启动,并捕获第二个Thread对象的句柄,然后调用wait()。第二个类的run()方法几秒后为第一个线程调用notifAll(),使第一个线程打印消息
  12. 一段C#学习代码(实现通过积分的几何意义计算积分)
  13. mysql存储过程事务和捕获异常信息
  14. caffe之学习曲线可视化
  15. 到底买苹果XS还是XR_iPhone XS和iPhone XR买哪个好?苹果XR和XS区别对比测评
  16. 假如你在泰坦尼克号上 你能活下来吗?——kaggle比赛泰坦尼克号数据集基于决策树
  17. 为什么会出现双摄像头手机?
  18. 国外最大的购物搜索/比较购物网站
  19. [深度学习论文笔记]UNETR: Transformers for 3D Medical Image Segmentation
  20. QT: skipping incompatible xx/xxx.dll when searching for -lxxx

热门文章

  1. 数据库表设计(一对多,多对多)
  2. Android 最佳实践
  3. 计算机网络 - 数据链路层 选择填空复习题
  4. Smith Numbers
  5. 父亲问我:“这些年你给家里贡献了什么?”
  6. 图片HSL颜色调节(仿QQ换肤)
  7. [附源码]计算机毕业设计基于springboot血库管理系统
  8. **matlab中 mean用法**
  9. iOS 获取手机IP地址
  10. oracle 表批量授权,oracle批量授权