zoukankan      html  css  js  c++  java
  • Redis事务、管道测试

    • PipeLine图解,在本地缓存,一次性发送

    IMPORTANT NOTE: While the client sends commands using pipelining, the server will be forced to queue the replies, using memory. So if you need to send a lot of commands with pipelining, it is better to send them as batches having a reasonable number, for instance 10k commands, read the replies, and then send another 10k commands again, and so forth. The speed will be nearly the same, but the additional memory used will be at max the amount needed to queue the replies for this 10k commands. https://redis.io/topics/pipelining

    • Transaction
      所有的指令在 exec 之前不执行,而是缓存在服务器的一个事务队列中,服务器一旦收到 exec 指令,才开执行整个事务队列,执行完毕后一次性返回所有指令的运行结果。因为 Redis 的单线程特性,它不用担心自己在执行队列的时候被其它指令打搅,可以保证他们能得到的「原子性」执行.

    • Maven

    <dependency>
                <groupId>org.apache.commons</groupId>
                <artifactId>commons-lang3</artifactId>
                <version>3.10</version>
    </dependency>
    <dependency>
                <groupId>redis.clients</groupId>
                <artifactId>jedis</artifactId>
                <version>2.4.2</version>
    </dependency>
    <dependency>
                <groupId>junit</groupId>
                <artifactId>junit</artifactId>
                <version>4.12</version>
                <scope>test</scope>
    </dependency>
    
    • 测试脚本
    package com.example.redis;
    
    import org.apache.commons.lang3.time.StopWatch;
    import org.junit.After;
    import org.junit.Before;
    import org.junit.Test;
    import redis.clients.jedis.Jedis;
    import redis.clients.jedis.Pipeline;
    import redis.clients.jedis.Transaction;
    
    import java.util.concurrent.TimeUnit;
    
    public class JedisTest {
    
        private static final String HOST = "localhost";
    
        private Jedis jedis;
    
        @Before
        public void setUp() {
            jedis = new Jedis(HOST);
        }
    
        @Test
        public void testGeneralSet() {
    
            StopWatch stopWatch = new StopWatch();
            stopWatch.start();
    
            for (int i = 0; i < 10000; i++) {
                jedis.set("key0:" + i, String.valueOf(i));
            }
            stopWatch.stop();
            System.out.println("普通的操作10000次字符串数据类型set写入,耗时:" + stopWatch.getTime(TimeUnit.MILLISECONDS) + "毫秒");
        }
    
        /**
         * 事务操作
         */
        @Test
        public void testTransaction() {
            StopWatch stopWatch = new StopWatch();
            stopWatch.start();
    
            Transaction transaction = jedis.multi();
    
            for (int i = 0; i < 10000; i++) {
                transaction.set("key3:" + i, String.valueOf(i));
            }
            transaction.exec();
    
            stopWatch.stop();
            System.out.println("事务操作10000次字符串数据类型set写入,耗时:" + stopWatch.getTime(TimeUnit.MILLISECONDS) + "毫秒");
        }
    
        /**
         * Pipeline批量提交
         * 最主要是为了控制网络开销
         */
        @Test
        public void testPipeline() {
            StopWatch stopWatch = new StopWatch();
            stopWatch.start();
    
            Pipeline pipeline = jedis.pipelined();
            for (int i = 0; i < 10000; i++) {
                pipeline.set("key1:" + i, String.valueOf(i));
            }
    
            //表示一次性的异步发送到redis,不关注执行结果。
            pipeline.sync();
            //程序会阻塞,等到所有命令执行完之后返回一个List集合
    //        pipeline.syncAndReturnAll();
            stopWatch.stop();
            System.out.println("pipeline操作10000次字符串数据类型set写入,耗时:" + stopWatch.getTime(TimeUnit.MILLISECONDS) + "毫秒");
        }
    
        /**
         *  Redis 事务在发送每个指令到事务缓存队列时都要经过一次网络读写,当一个事务内部的指令较多时,需要的网络 IO 时间也会线性增长。
         *  所以通常 Redis 的客户端在执行事务时都会结合 pipeline 一起使用,这样可以将多次 IO 操作压缩为单次 IO 操作
         */
        @Test
        public void testPipelineWithTransaction() {
            StopWatch stopWatch = new StopWatch();
            stopWatch.start();
    
            Pipeline pipeline = jedis.pipelined();
    
            pipeline.multi();
            for (int i = 0; i < 10000; i++) {
                pipeline.set("key2:" + i, String.valueOf(i));
            }
            pipeline.exec();
    
            //表示一次性的异步发送到redis,不关注执行结果。
            pipeline.sync();
            stopWatch.stop();
            System.out.println("带事务的pipeline操作10000次字符串数据类型set写入,耗时:" + stopWatch.getTime(TimeUnit.MILLISECONDS) + "毫秒");
        }
    
        @After
        public void tearDown()  {
            jedis.close();
        }
    }
    
    
  • 相关阅读:
    java8学习之Collector复合与注意事项
    动画学习之WIFI图形绘制
    java线程基础巩固---多线程死锁分析,案例介绍
    java8学习之Collector同一性与结合性分析
    java8学习之Collector源码分析与收集器核心
    java8学习之Stream分组与分区详解
    kotlin面向对象之抽象类、继承、多态
    matplotlib-曲线和折线案例
    人口、人口密度分析项目-条形图
    开机自启:bat实现一次性打开win7中的常用软件和文件夹
  • 原文地址:https://www.cnblogs.com/zendwang/p/redis-feature-pipeline-and-transaction-test.html
Copyright © 2011-2022 走看看