Redis(十) Java客户端

在这里插入图片描述

文章目录

  • 前言
  • SSH端口转发
  • Jedis的使用
    • Redis 通用命令的使用
    • Redis String 类型命令的使用
    • Redis List 类型命令使用
    • Redis Hash 类型命令的使用
    • Redis Set 类型的使用
    • Redis Zset 类型命令的使用

前言

前面我们学习 redis 的时候都是在 redis 的原生客户端上输入 redis 命令的,由于 Redis 服务器官网公开了使用的协议——RESP,所有任何一个第三方都可以通过 RESP 协议来实现出一个和 redis 服务器通信的客户端程序。同样我们的 Java 也是。

有很多大佬开发出了相关的库,我们可以直接使用,这样我们程序眼就不必过多关注 RESP 协议的细节了。在 Java 生态中,封装了 RESP 协议实现的客户端有很多,在这里我们介绍的是其中的一个 JEDIS。

SSH端口转发

平时我们使用 Java 开发的时候,往往使用的平台是 Windows,而 Redis 服务器往往是在 Linux 系统上的,所以我们 Windows 用户要想使用 Linux 系统,最简单的方法就是买一个 Linux 云服务器,然后通过第三方软件来远程连接我们的 Linux 云服务器,这个第三方软件通常使用 SSH 协议来连接我们的云服务器的,那么我们的 Java 程序如何访问到我们的云服务上面的 Redis 服务器呢?

很多人可能会说,云服务器不是使用的公网 IP 吗,只要知道我们云服务器的 IP 地址和 Redis 的端口号不就能访问到这台云服务器上面的 Redis 服务器了吗?想法是好的,但是实际上行不通,如果我们放开云服务器的 6379 Redis 服务器端口,这样我们是可以访问到这台云服务器上面的 Redis 服务器,但是可能不出三天,你的这台云服务器就会被黑客给入侵了。既然这样的话,那么我们前面在使用 Java 的 Spring 的时候,要想访问我们写的程序,那么就需要将 Java 程序部署到 Linux 服务器上才能使用,那么这不也开放了 8080 端口吗?那这为什么可以呢?这是因为 Java 使用的端口黑客要是想攻击,需要花费的成本就会很高,而我们的 Redis 服务器使用的端口黑客要是想攻击,成本就相对较低,那么如果我更换 Redis 服务器使用的端口是否能解决这个问题呢?答案是不能的,这样做就相当于只是更换了门的位置,但是门上面的锁没有更换,是一样的。

那么既然这样的话,是否就意味着我们的 Java 程序无法访问到云服务上面的 Redis 服务器吗?这也不是的,为了保证 Java 程序也能访问到云服务器上面的 Redis 服务,有两种解决方法:

  1. 当写完 Java 程序之后,将 Java 程序打成 jar 包,然后部署到云服务器上面,这样客户端和服务器端就在一个机器上了,这样就不容易产生安全问题了。这样虽然可以解决,但是比较麻烦。
  2. 配置 SSH 端口转发

SSH端口转发是一种通过SSH协议在本地和远程主机之间建立安全通道,实现端口之间的数据转发的技术。它允许用户在不直接访问目标主机的情况下,通过安全的SSH连接来访问该主机上的服务。SSH端口转发基于SSH协议的加密和身份验证机制,确保传输的数据安全可靠。

SSH端口转发有两种主要类型:本地端口转发和远程端口转发。本地端口转发将远程计算机上的服务转发到本地计算机,使得本地计算机能够通过SSH隧道访问远程计算机上的服务。而远程端口转发则将本地计算机上的服务转发到远程计算机,实现远程计算机对本地服务的访问。

我们这里使用的是将远程计算机上的服务转发到本地计算机:

我这里使用的是 xshell 来连接我的云服务器,在 xshell 中右击我们要使用的云服务器,然后选择属性:
在这里插入图片描述
选择隧道 -> 添加:

在这里插入图片描述
在这里插入图片描述

确定之后,重启我们的云服务器,并且如果需要使用远程计算机上的服务,需要保证我们的 xshell 和 云服务器是处于连接状态,我们可以在本地计算机上使用 netstat -ano | findstr 8888来查看是否绑定成功。

在这里插入图片描述
如果没有绑定成功,或者 xshell 没有连接上云服务就查找不到这个端口。

不仅如此,为了能使我们的 Java 程序能成功访问到云服务器上的 Redis 服务,我们还需要设置 redis 的配置文件:

在这里插入图片描述

Jedis的使用

当完成 SSH 端口的映射之后,我们就可以说在 Java 程序中访问我们云服务器上的 Redis 服务器了。

首先因为 Jedis 属于第三方库,所以首先需要将 Jedis 的 maven 坐标导入到我们的项目中。

在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
导入依赖之后,我们就可以使用 Jedis 了。

Redis 通用命令的使用

要想使用 Jedis,首先我们需要先得到一个类似 JedisPool 的池,然后再从这个 JedisPoll 中拿到 Jedis 对象:

import redis.clients.jedis.Jedis;
import redis.clients.jedis.JedisPool;public class RedisDemoGeneric {public static void main(String[] args) {JedisPool jedisPool = new JedisPool("tcp://127.0.0.1:8888");try (Jedis jedis = jedisPool.getResource()) {}}
}

我们之所以选择 Jedis 作为 Java 的 Redis 客户端,是因为 Jedis 的方法和 Redis 的命令有极大的相似性,这样就降低了我们的学习成本。

test1();public static void test1(Jedis jedis) {jedis.flushAll();  //首先清空数据库,防止每次调用方法的时候,里面的数据造成影响String pong = jedis.ping();System.out.println(pong);}

在这里插入图片描述
这里的红色不是报错,暂时先不用管。

public static void test1(Jedis jedis) {jedis.flushAll();  //首先清空数据库,防止每次调用方法的时候,里面的数据造成影响String pong = jedis.ping();System.out.println(pong);jedis.set("key","111");String value = jedis.get("key");System.out.println(value);}

在这里插入图片描述
可以看到这里面有很多种方法:

在这里插入图片描述
如果我们在使用 set 方法的时候需要指定其他选项的时候,可以传入一个 SetParams 类型的参数:

在这里插入图片描述

public static void test1(Jedis jedis) {SetParams setParams = new SetParams();setParams.ex(30);setParams.nx();jedis.set("key1","111",setParams);long time = jedis.ttl("key1");System.out.println(time);}

在这里插入图片描述

jedis.set("key","111");
boolean result = jedis.exists("key"); //判断key是否存在
System.out.println("result: " + result);

在这里插入图片描述

jedis.set("key","111");
jedis.set("key2","222");
long del = jedis.del("key"); //删除key
System.out.println("del: " +del);
boolean v1 = jedis.exists("key");
boolean v2 = jedis.exists("key2");
System.out.println("v1: " + v1);
System.out.println("v2: " + v2);

在这里插入图片描述

jedis.set("key1","111");
jedis.set("key2","222");
jedis.set("key3","333");
Set<String> keys = jedis.keys("*"); //对于keys命令的返回值,需要使用set类型来接收,因为redis中key是不可以重复的
System.out.println("keys: " + keys);

在这里插入图片描述

jedis.set("key1","111");
String type = jedis.type("key1");
System.out.println("type: " + type);
jedis.lpush("key2","111","222");
type = jedis.type("key2");
System.out.println("type: " + type);
jedis.hset("key3","f1","111");
type = jedis.type("key3");
System.out.println("type: " + type);
jedis.sadd("key4","111","222");
type = jedis.type("key4");
System.out.println("type: " + type);
jedis.zadd("key5",90.5,"111");
type = jedis.type("key5");
System.out.println("type: " + type);

在这里插入图片描述

Redis String 类型命令的使用

public static void test2(Jedis jedis) {jedis.flushAll();jedis.mset("key1","111","key2","222","key3","333");List<String> list = jedis.mget("key1","key2","key3");System.out.println("list: " + list);
}

在这里插入图片描述

jedis.set("key1","abcdefg");
String v = jedis.get("key1");
System.out.println("v: " + v);
jedis.setrange("key1",2,"xyz");
v = jedis.getrange("key1",0,-1);
System.out.println("v: " + v);

在这里插入图片描述

jedis.set("key1","abcdefg");
String v = jedis.get("key1");
System.out.println("v: " + v);
jedis.append("key1","xyz");
v = jedis.get("key1");
System.out.println("v: " + v);

在这里插入图片描述

jedis.set("key1","10");
String v = jedis.get("key1");
System.out.println("v: " + v);
long result = jedis.incr("key1");
System.out.println("result: " + result);
result = jedis.decr("key1");
System.out.println("result: " + result);
result = jedis.incrBy("key1",10);
System.out.println("result: " + result);
result = jedis.decrBy("key1",20);
System.out.println("result: " + result);
double d = jedis.incrByFloat("key1",13.14);
System.out.println("d: " + d);

在这里插入图片描述

Redis List 类型命令使用

jedis.flushAll();jedis.lpush("key1","111","222","333"); //头插
List<String> list = jedis.lrange("key1",0,-1);
System.out.println("list: " + list);

在这里插入图片描述

jedis.rpush("key1","111","222","333");
List<String> list = jedis.lrange("key1",0,-1);
System.out.println("list: " + list);
String pop = jedis.lpop("key1");
System.out.println("lpop: " + pop);
pop = jedis.rpop("key1");
System.out.println("rpop: " + pop);

在这里插入图片描述

List<String> list = jedis.lrange("key1",0,-1);
System.out.println("list: " + list);
list = jedis.blpop(300,"key1","key2");
System.out.println("list: " + list);

在这里插入图片描述
在这里插入图片描述

Redis Hash 类型命令的使用

jedis.flushAll();//hset可以一次只设置一对file-value
jedis.hset("key1","f1","111");
String v = jedis.hget("key1","f1");
System.out.println("v: " + v);
//hset也可通过map来一次设置多对file-set
Map<String,String> map = new HashMap<>();
map.put("f1","111");
map.put("f2","222");
jedis.hset("key2",map);
v = jedis.hget("key2","f2");
System.out.println("v: " + v);

在这里插入图片描述

jedis.hset("key1","f1","111");
boolean b = jedis.hexists("key1","f1");
System.out.println("b: " + b);
b = jedis.hexists("key1","key2");
System.out.println("b: " + b);

在这里插入图片描述

jedis.hset("key1","f1","111");
jedis.hdel("key1","f1");
String s = jedis.hget("key1","f1");
System.out.println("s: " + s);

在这里插入图片描述

Map<String,String> map = new HashMap<>();
map.put("f1","111");
map.put("f2","222");
map.put("f3","333");
map.put("f4","444");
jedis.hset("key1",map);
Set<String> set = jedis.hkeys("key1");
System.out.println("keys: " + set);
List<String> list = jedis.hvals("key1");
System.out.println("values: " + list);

在这里插入图片描述

Map<String,String> map = new HashMap<>();
map.put("f1","111");
map.put("f2","222");
map.put("f3","333");
map.put("f4","444");
jedis.hmset("key1",map);
List<String> list = jedis.hmget("key1","f1","f2","f4");
System.out.println("list: " + list);

在这里插入图片描述

Redis Set 类型的使用

jedis.flushAll();jedis.sadd("key1","111","222","444","333");
Set<String> set = jedis.smembers("key1");
System.out.println("members: " + set);

在这里插入图片描述

jedis.sadd("key1","111","222","444","333");
Set<String> set = jedis.smembers("key1");
boolean b = jedis.sismember("key1","111");
System.out.println("b: " + b);
b = jedis.sismember("key1","10101010");
System.out.println("b: " + b);

在这里插入图片描述

jedis.sadd("key1","111","222","444","333");
long len = jedis.scard("key1");
System.out.println("len: " + len);

在这里插入图片描述

jedis.sadd("key1","111","222","444","333");
String pop = jedis.spop("key1");
System.out.println("pop: " + pop);
pop = jedis.spop("key1");
System.out.println("pop: " + pop);
pop = jedis.spop("key1");
System.out.println("pop: " + pop);
pop = jedis.spop("key1");
System.out.println("pop: " + pop);
pop = jedis.spop("key1");
System.out.println("pop: " + pop);

在这里插入图片描述

jedis.sadd("key1","111","222","444","333");
jedis.sadd("key2","111","222","777","888");
Set<String> set = jedis.sinter("key1","key2");
System.out.println("inter: " + set);

在这里插入图片描述

jedis.sadd("key1","111","222","444","333");
jedis.sadd("key2","111","222","777","888");
long len = jedis.sinterstore("key3","key1","key2");
System.out.println("len: " + len);
Set<String> set = jedis.smembers("key3");
System.out.println("set: " + set);

在这里插入图片描述

Redis Zset 类型命令的使用

jedis.zadd("key1",93.5,"zhangsan");
List<String> list = jedis.zrange("key1",0,-1);
System.out.println("set: " + list);
List<Tuple> tuple = jedis.zrangeWithScores("key1",0,-1);
System.out.println("tuple: " + tuple);

在这里插入图片描述

Map<String,Double> map = new HashMap<>();
map.put("zhangsan",93.0);
map.put("lisi",95.5);
map.put("wangwu",100.0);
jedis.zadd("key1",map);
List<String> list = jedis.zrange("key1",0,-1);
System.out.println("list: " + list);
List<Tuple> tuple = jedis.zrangeWithScores("key1",0,-1);
System.out.println("tuple: " + tuple);

在这里插入图片描述

Map<String,Double> map = new HashMap<>();
map.put("zhangsan",93.0);
map.put("lisi",95.5);
map.put("wangwu",100.0);
jedis.zadd("key1",map);
long len = jedis.zcard("key1");
System.out.println("len: " + len);

在这里插入图片描述

Map<String,Double> map = new HashMap<>();
map.put("zhangsan",93.0);
map.put("lisi",95.5);
map.put("wangwu",100.0);
jedis.zadd("key1",map);
long count = jedis.zrem("key1","zhangsan","lisi");
System.out.println("count: " + count);
List<Tuple> tuple = jedis.zrangeWithScores("key1",0,-1);
System.out.println("tuple: " + tuple);

在这里插入图片描述

Map<String,Double> map = new HashMap<>();
map.put("zhangsan",93.0);
map.put("lisi",95.5);
map.put("wangwu",100.0);
jedis.zadd("key1",map);
Double score = jedis.zscore("key1","zhangsan"); //这里尽量使用包装类,因为如果要获取的分数的元素不在zset中就会返回null,而普通类型double无法接收null
System.out.println("score: " + score);
score = jedis.zscore("key1","zhaoliu");
System.out.println("score: " + score);

在这里插入图片描述

Map<String,Double> map = new HashMap<>();
map.put("zhangsan",93.0);
map.put("lisi",95.5);
map.put("wangwu",100.0);
jedis.zadd("key1",map);
Long rank = jedis.zrank("key1","zhangsan"); //这里同样使用包装类
System.out.println("rank: " + rank);
rank = jedis.zrank("key1","lisi");
System.out.println("rank: " + rank);
rank = jedis.zrank("key1","wangwu");
System.out.println("rank: " + rank);
rank = jedis.zrank("key1","zhaoliu");
System.out.println("rank: " + rank);

在这里插入图片描述
如果我们使用 jedis 的时候遇到了问题,可以去 GitHub 上 jedis 的官方文档去看看。https://github.com/redis/jedis

在这里插入图片描述

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://xiahunao.cn/news/3020263.html

如若内容造成侵权/违法违规/事实不符,请联系瞎胡闹网进行投诉反馈,一经查实,立即删除!

相关文章

npm安装指定版本,npm删除依赖,卸载依赖

安装指定版本 npm中安装指定的版本号&#xff0c;格式为 ‘包名版本号’ npm install 包名称版本号 --save 例如安装jquery: npm install jquery3.0.0 --save在package.json里面可以看到对应的包&#xff1a; "jquery": "^3.0.0"注意&#xff1a;已有…

解决硬盘灯不停的闪硬盘不停的读cpu占用率高的Microsoft Windows Search

可能你发现了&#xff0c;你的硬盘灯一直亮着&#xff0c;为什么&#xff1f;&#xff1f;可能你发现了&#xff0c;你的CPU占用率一直居高不下&#xff0c;为什么&#xff1f;也许就是因为Microsoft Windows Search这个进程 一、windowsSearch的罪证 SearchIndexer和Search…

2024 CorelDraw最新图形设计软件 激活安装教程来了

2024年3月&#xff0c;备受瞩目的矢量制图及设计软件——CorelDRAW Graphics Suite 2024 正式面向全球发布。这一重大更新不仅是 CorelDRAW 在 36 年创意服务历史中的又一重要里程碑&#xff0c;同时也展现了其在设计软件领域不断创新和卓越性能的领导地位。 链接: https://pan…

7天精通Web APIs——-Bom操作(理论+实战)(第五天)

一、window对象 1.1 window对象和bom的关系 首先理解dom和bom之间的关系 显然bom的范围比较大 bom的全称为浏览器对象模型 window是bom的核心对象&#xff0c;window里面有很多属性和方法&#xff0c;用于实现浏览器与 JavaScript 代码之间的交互。作为 JavaScript 的全局对…

电脑提示‘找不到msvcr110dll,无法继续执行代码’的解决方法,3分钟快速修复

不知道大家有没有遇到过这种情况&#xff0c;无端端电脑提示你找不到msvcr110dll,无法继续执行代码&#xff1f;当出现这个情况&#xff0c;证明你的某个程序就已经运行不了&#xff0c;你需要去修复这个错误&#xff0c;才能正常的运行程序&#xff0c;下面我们一起来详细的了…

Java集合 总结篇(全)

Java集合 集合底层框架总结 List 代表的有序&#xff0c;可重复的集合。 ArrayList -- 数组 -- 把他想象成C中的Vector就可以&#xff0c;当数组空间不够的时候&#xff0c;会自动扩容。 -- 线程不安全 LinkedList -- 双向链表 -- 可以将他理解成一个链表&#xff0c;不支持…

TSINGSEE青犀视频边缘计算AI智能分析网关V4告警消息语音推送的配置流程

TSINGSEE青犀视频边缘计算硬件智能分析网关V4内置了近40种AI算法模型&#xff0c;支持对接入的视频图像进行人、车、物、行为等实时检测分析&#xff0c;上报识别结果&#xff0c;并能进行语音告警播放。今天我们来分享一下如何配置和使用AI智能分析网关V4的语音推送。 提前准备…

docker私有仓库的registry

简介 Docker私有仓库的Registry是一个服务&#xff0c;主要用于存储、管理和分发Docker镜像。具体来说&#xff0c;Registry的功能包括&#xff1a; 存储镜像&#xff1a;Registry提供一个集中的地方来存储Docker镜像&#xff0c;包括镜像的层次结构和元数据。 版本控制&…

【Qt】常用控件(一)

文章目录 一、核心属性1、enabled代码示例: 通过按钮2 切换按钮1 的禁用状态 2、geometry代码示例: 控制按钮的位置代码示例&#xff1a;window frame 的影响代码示例: 感受 geometry 和 frameGeometry 的区别 3、windowTitle4、windowIcon代码示例: 通过 qrc 管理图片作为图标…

小米手机怎么截屏?一篇文章教会你!

我们经常需要截取手机屏幕上的内容&#xff0c;无论是为了分享、教学还是记录。对于小米手机用户来说&#xff0c;掌握截屏技巧不仅能够方便地记录精彩瞬间&#xff0c;还能在需要时轻松分享或保存屏幕内容。小米手机怎么截屏&#xff0c;有哪些截屏方式呢&#xff1f;本文将为…

软件测试实战项目(含电商、银行、APP等)

&#x1f345; 视频学习&#xff1a;文末有免费的配套视频可观看 &#x1f345; 关注公众号【互联网杂货铺】&#xff0c;回复 1 &#xff0c;免费获取软件测试全套资料&#xff0c;资料在手&#xff0c;涨薪更快 今天给大家带来几个软件测试项目的实战总结及经验&#xff0c;适…

指定地区|CSC高级研究学者赴澳大利亚访学交流

CSC高级研究学者均是正高或博导级的&#xff0c;学术背景较强&#xff0c;多数能DIY联系到国外合作机构。但也有些申请者因指定地域或学校&#xff0c;或须在短期内获取邀请函故而求助于我们。本案例D教授就指定澳大利亚的墨尔本地区&#xff0c;我们最终用维多利亚大学的邀请函…

taro3兼容支付宝/微信小程序的自定义拖拽排序组件

描述&#xff1a;列表可以完成拖拽排序 此组件是根据支付宝原生文档改编成taro-vue3的形式&#xff0c;只保留了拖拽的部分&#xff0c;其他功能都去除了&#xff0c;测试下来可以兼容支付宝和微信小程序。 支付宝原生文档&#xff1a; https://opendocs.alipay.com/support/…

Linux下使用RAID

目录 1. 创建RAID准备 2. 创建RAID 0 2.1. 创建磁盘阵列 &#xff08;1&#xff09;创建磁盘阵列 &#xff08;2&#xff09;查看磁盘阵列信息 &#xff08;3&#xff09;挂载文件系统 &#xff08;4&#xff09;保存RAID信息 &#xff08;5&#xff09;开机自动挂载RA…

字符编码(十六进制)

题目描述 假设一个简易的变长编码规则XUTF:每个字符有一个唯一编号值 unicodeVal(如汉字“华”的编号十进制值是21326),使用1~6个字节进行编码,编码规则如下: 编码格式: 编号值范围编码后字节长度n二进制格式(x 表示有效位,其它为固定位)[0, 2^7)1字节1xxxxxxx[2^7,…

3dmax-vray6渲染器参数设置

适用于3dmax2018-2023版本 一、【公用】 小图输出大小:1500*1125&#xff0c;勾选大气、效果&#xff1b; 大图输出大小:3000*2250&#xff0c;勾选大气、效果、置换&#xff1b; 二、【vray】 小图抗锯齿类型:渐进式&#xff1b;最小细分:1&#xff0c;最大细分:100&#…

Day_3

1. HttpClient HttpClient是Apache的一个子项目&#xff0c;是高效的、功能丰富的支持HTTP协议的客户端编程工具包 作用&#xff1a;发送HTTP请求&#xff0c; 接受相应数据 <dependency><groupId>org.apache.httpcomponents</groupId><artifactId>…

B1506脉冲测试中的孔径

孔径&#xff08;Aperture Time&#xff09;是示波器或测量设备中使用的一个术语&#xff0c;指的是在一次测量中&#xff0c;示波器或测量设备对信号进行采样的时间长度。在进行波形捕获或测量时&#xff0c;孔径时间决定了采样的持续时间&#xff0c;从而影响测量的分辨率和准…

视频提取gif怎么制作?试试这个网站一键转换

通过把视频转换成gif动图的操作能够更加方便的在各种平台上分享和传播。相较于视频&#xff0c;gif图片具有较小的文件体积&#xff0c;gif动图能够快速的加载播放&#xff0c;不需要等待就能快速欣赏。很适合从事新媒体之类的小伙伴&#xff0c;可以用来做展示、宣传等。想要实…

添砖Java之路其二——基本数据类型,scanner,字符拼接。

目录 基本数据类型&#xff1a; ​编辑 Scanner: 字符拼接&#xff1a; 课后小题&#xff1a; 基本数据类型&#xff1a; 如图可见&#xff1a;Java里面有八种基本数据类型。 注意&#xff1a;在其中我们需要注意的是int默认整型数据&#xff0c;double是默认浮点型数据。因…