java redis 管道_redis 管道

管道(pipeline)将客户端 client 与服务器端的交互明确划分为单向的发送请求(Send Request)和接收响应(Receive Response):用户可以将多个操作连续发给服务器,但在此期间服务器端并不对每个操作命令发送响应数据;全部请求发送完毕后用户关闭请求,开始接收响应获取每个操作命令的响应结果。

管道(pipeline)在某些场景下非常有用,比如有多个操作命令需要被迅速提交至服务器端,但用户并不依赖每个操作返回的响应结果,对结果响应也无需立即获得,那么管道就可以用来作为优化性能的批处理工具。性能提升的原因主要是减少了 TCP 连接中交互往返的开销。

不过在程序中使用管道请注意,使用 pipeline 时客户端将独占与服务器端的连接,此期间将不能进行其他“非管道”类型操作,直至 pipeline 被关闭;如果要同时执行其他操作,可以为 pipeline 操作单独建立一个连接,将其与常规操作分离开来。

代码示例-性能对比public class RedisPipelinePerformanceDemo {

public static void main(String[] args) {

Jedis jedis = new Jedis(host, port);

//ApsaraDB for Redis的实例密码

String authString = jedis.auth(host+":"+password);// password

if (!authString.equals("OK")) {

System.err.println("AUTH Failed: " + authString);

jedis.close();

return;

}

//连续执行多次命令操作

final int COUNT=5000;

String key = "KVStore-Tanghan";

// 1 ---不使用pipeline操作---

jedis.del(key);//初始化key

Date ts1 = new Date();

for (int i = 0; i 

//发送一个请求,并接收一个响应(Send Request and  Receive Response)

jedis.incr(key);

}

Date ts2 = new Date();

System.out.println("不用Pipeline > value为:"+jedis.get(key)+" > 操作用时:" + (ts2.getTime() - ts1.getTime())+ "ms");

//2 ----对比使用pipeline操作---

jedis.del(key);//初始化key

Pipeline p1 = jedis.pipelined();

Date ts3 = new Date();

for (int i = 0; i 

//发出请求 Send Request

p1.incr(key);

}

//接收响应 Receive Response

p1.sync();

Date ts4 = new Date();

System.out.println("使用Pipeline > value为:"+jedis.get(key)+" > 操作用时:" + (ts4.getTime() - ts3.getTime())+ "ms");

jedis.close();

}

}

运行结果

不用Pipeline > value为:5000 > 操作用时:211707ms

使用Pipeline > value为:5000 > 操作用时:609ms

代码示例-响应数据的两种处理方式public class PipelineClientDemo {

public static void main(String[] args) {

Jedis jedis = new Jedis(host, port);

// ApsaraDB for Redis的实例密码

String authString = jedis.auth(host+":"+password);// password

if (!authString.equals("OK")) {

System.err.println("AUTH Failed: " + authString);

jedis.close();

return;

}

String key = "KVStore-Test1";

jedis.del(key);//初始化

// -------- 方法1

Pipeline p1 = jedis.pipelined();

System.out.println("-----方法1-----");

for (int i = 0; i 

p1.incr(key);

System.out.println("Pipeline发送请求");

}

// 发送请求完成,开始接收响应

System.out.println("发送请求完成,开始接收响应");

List responses = p1.syncAndReturnAll();

if (responses == null || responses.isEmpty()) {

jedis.close();

throw new RuntimeException("Pipeline error: 没有接收到响应");

}

for (Object resp : responses) {

System.out.println("Pipeline接收响应Response: " + resp.toString());

}

System.out.println();

//-------- 方法2

System.out.println("-----方法2-----");

jedis.del(key);//初始化

Pipeline p2 = jedis.pipelined();

//需要先声明Response

Response r1 = p2.incr(key);

System.out.println("Pipeline发送请求");

Response r2 = p2.incr(key);

System.out.println("Pipeline发送请求");

Response r3 = p2.incr(key);

System.out.println("Pipeline发送请求");

Response r4 = p2.incr(key);

System.out.println("Pipeline发送请求");

Response r5 = p2.incr(key);

System.out.println("Pipeline发送请求");

try{

r1.get();  //此时还未开始接收响应,所以此操作会出错

}catch(Exception e){

System.out.println(" <<>> ");

}

// 发送请求完成,开始接收响应

System.out.println("发送请求完成,开始接收响应");

p2.sync();

System.out.println("Pipeline接收响应Response: " + r1.get());

System.out.println("Pipeline接收响应Response: " + r2.get());

System.out.println("Pipeline接收响应Response: " + r3.get());

System.out.println("Pipeline接收响应Response: " + r4.get());

System.out.println("Pipeline接收响应Response: " + r5.get());

jedis.close();

}

}

运行结果-----方法1-----

Pipeline发送请求

Pipeline发送请求

Pipeline发送请求

Pipeline发送请求

Pipeline发送请求

发送请求完成,开始接收响应

Pipeline接收响应Response: 1

Pipeline接收响应Response: 2

Pipeline接收响应Response: 3

Pipeline接收响应Response: 4

Pipeline接收响应Response: 5

-----方法2-----

Pipeline发送请求

Pipeline发送请求

Pipeline发送请求

Pipeline发送请求

Pipeline发送请求

<<>>

发送请求完成,开始接收响应

Disconnected from the target VM, address: '127.0.0.1:59635', transport: 'socket'

Pipeline接收响应Response: 1

Pipeline接收响应Response: 2

Pipeline接收响应Response: 3

Pipeline接收响应Response: 4

Pipeline接收响应Response: 5

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
Java 中操作 Redis管道可以显著降低网络延迟,提高 Redis 操作的性能。Java 操作 Redis管道可以通过 Jedis 或者 Lettuce 完成。 下面是使用 Jedis 操作 Redis 管道的示例代码: ```java Jedis jedis = new Jedis("localhost"); Pipeline pipeline = jedis.pipelined(); pipeline.set("key1", "value1"); pipeline.set("key2", "value2"); pipeline.set("key3", "value3"); List<Object> results = pipeline.syncAndReturnAll(); ``` 在这个示例中,我们首先创建了一个 Jedis 实例,并通过它创建了一个 Pipeline 实例。然后我们使用 Pipeline 实例执行了三个 set 操作,最后通过 pipeline.syncAndReturnAll() 方法执行这些操作并获取它们的返回值。 使用 Lettuce 操作 Redis 管道的示例代码如下: ```java RedisClient redisClient = RedisClient.create("redis://localhost"); StatefulRedisConnection<String, String> connection = redisClient.connect(); RedisCommands<String, String> commands = connection.sync(); RedisPipeline pipeline = connection.reactive().multi(); CompletableFuture<String> future1 = pipeline.set("key1", "value1"); CompletableFuture<String> future2 = pipeline.set("key2", "value2"); CompletableFuture<String> future3 = pipeline.set("key3", "value3"); pipeline.exec(); CompletableFuture.allOf(future1, future2, future3).join(); ``` 在这个示例中,我们首先创建了一个 RedisClient 实例,并通过它创建了一个 StatefulRedisConnection 实例。然后我们使用它创建了一个 RedisPipeline 实例,并通过它执行了三个 set 操作。最后,我们通过 pipeline.exec() 方法执行这些操作并等待它们的完成。 总的来说,使用管道可以使 Redis 的操作变得更加高效,但是需要注意的是,管道操作是无法回滚的,因此在使用管道操作时需要特别小心。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值