redisのマルチコマンド実行方法の1つ-pipeling

2448 ワード

パイプ転送(pipelining):複数のredisコマンドを一度に処理するために使用されます.
redisの実行プロセスはクライアントにコマンドをサービス側に送信し、カスタマーサービス側がサービス側プログラムの戻りを待つのをブロックし、中間がネットワーク通信の問題で速度が遅い場合、またクライアントとサービス側のデータ伝送に一定の時間がかかる.これ
時間はRTT、Round Trip Timeと呼ばれています.一度に転送するコマンドがたくさんある場合は、相対的に遅くなります.redisはpipeliningコマンドを提供して処理します.
pipelingは従来のコマンド伝送方式では、クライアントが複数のコマンドを送信して伝送中に消費される時間を減らすことができ、redisは早くからこの問題を考慮しているので、バージョンの互換性の問題を心配する必要はありません.
最も簡単なバージョンは次のとおりです.
          
  • Client: INCR X
  • Client: INCR X
  • Client: INCR X
  • Client: INCR X
  • Server: 1
  • Server: 2
  • Server: 3
  • Server: 4

  • このようなコマンドに似ています.$ (printf "PING\r
    PING\r
    PING\r
    "; sleep 1) | nc localhost 6379
    +PONG
    +PONG
    +PONG

    注意事項:
    クライアントがpipeliningを使用して複数の命令を送信すると、サーバ側は処理後の結果を強制的にソートします.そのため、一度に大量のコマンドを転送する必要があり、サービス側のメモリに制限がある場合は、20 Kの数のコマンドを転送するなど、合理的な番号を付けたほうがいいです.まず10 Kのコマンドを転送することができます.
    Redisのサービス側に戻りを待ち、戻ったデータを取得してから再び10 Kのコマンドをサーバに送信すると、処理効率は実は近いが、メモリの半分を節約できる.
    次のpythonスクリプトを使用して、従来の方法とpipeliningを使用した処理中の時間の違いをテストします.require 'rubygems'
    require 'redis'

    def bench(descr)
        start = Time.now
        yield
        puts "#{descr} #{Time.now-start} seconds"
    end

    def without_pipelining
        r = Redis.new
        10000.times {
            r.ping
        }
    end

    def with_pipelining
        r = Redis.new
        r.pipelined {
            10000.times {
                r.ping
            }
        }
    end

    bench("without pipelining") {
        without_pipelining
    }
    bench("with pipelining") {
        with_pipelining

    }
    上記のスクリプトを使用して、同じmacノートパソコンでのテスト結果は次のとおりです.without pipelining 1.185238 seconds
    with pipelining 0.250783 seconds

    pipelingを使用すると、多くの時間を節約できることがわかります.
    redis piplingとredis scriptスクリプトの比較
    シーン1、redis 2.6以降はredis scriptを使って
    サーバのredis-cli側で大量のコマンドを実行する必要がある場合はpipeliningではなくredis scriptを使用します.
    原因分析:
    しかし、redis scriptの優れた特徴は、read write computeを同時に行うことができることです.例えば、redisスクリプトで在庫を読み出して1を減らし、他の商品の在庫と比較するなどの操作ができるシーンでは、redis scriptは非常に速いですが、このシーンではpipelingではあまり適切ではありません.
    シーン2、場合によっては
    pipelingはevalまたはevalshaコマンドをサービス側に送信します.pipelingはこの機能を完璧にサポートしているため、script loadメソッドでスクリプトコンテンツをロードする必要があることを明確に指定しています.
    これによりevalshaのsha検証が存在せず、スクリプトが見つからない場合を防止できます.