ホームページ  >  記事  >  データベース  >  Redis6 のシングルスレッド モデルとマルチスレッド モデルの簡単な分析

Redis6 のシングルスレッド モデルとマルチスレッド モデルの簡単な分析

青灯夜游
青灯夜游転載
2022-01-26 10:38:023309ブラウズ

この記事では、Redis6 のスレッド モデルを理解し、シングル スレッド モデルとマルチ スレッド モデルを紹介します。

Redis6 のシングルスレッド モデルとマルチスレッド モデルの簡単な分析

1. Redis の進化の歴史

単純に Redis がシングルスレッドかマルチスレッドかというと、この答えになります。バージョンによって使用されるスレッド モデルは異なります。 [関連する推奨事項: Redis ビデオ チュートリアル ]

Redis6 のシングルスレッド モデルとマルチスレッド モデルの簡単な分析

  • # 最も初期のバージョンであるバージョン 3.x は、口コミで誰もが広めるものです。口 Redis はシングルスレッドです。

  • バージョン 4.x は、厳密に言えばシングルスレッドではありませんが、クライアント要求の処理を担当するスレッドはシングルスレッドですが、いくつかの

    multi が追加され始めています。 -スレッド関連 (非同期削除)

  • 最新バージョン 6.0 以降。

    #2. Redis シングルスレッド モデル

2.1 シングルスレッドの本当の意味

主に、Redis のネットワーク IO とキーと値のペアの読み取りと書き込みが 1 つのスレッドで完了することを意味します。Redis がクライアントのリクエストを処理する際には、取得 (ソケットの読み取り)、解析、実行、コンテンツの返却 (ソケット) が含まれます。書き込みなど)など。順次メインスレッドによって処理されます。これは「シングルスレッド」と呼ばれます。これは、Redis が外部のキーと値のストレージ サービスを提供するための主要なプロセスでもあります。 ただし、

永続化、非同期削除、クラスター データの同期などの Redis の他の機能は、実際には

追加のスレッドRedis6 のシングルスレッド モデルとマルチスレッド モデルの簡単な分析によって実行されます。​ Redis ワーカー スレッドはシングルスレッドであると言えます。ただし、
Redis 全体はマルチスレッドです;2.2 シングルスレッドのパフォーマンスが高速な理由

Redis 3 .x シングルスレッド時代ですが、

高速パフォーマンスの主な理由: メモリ操作に基づく: すべてのデータはメモリに保存されるため、すべての操作はメモリ レベルで行われます

単純なデータ構造: Redis のデータ構造は特別に設計されており、ほとんどの場合、これらの単純なデータ構造の検索と操作の複雑さは #o(1)

    多重化とブロック化IO: IO 多重化機能を使用してクライアントへの複数のソケット接続を監視すると、1 つのスレッド接続で複数のリクエストを処理できるようになり、スレッドの切り替えによって発生するオーバーヘッドが軽減され、IO ブロック操作が回避されます。コンテキストスイッチング: シングルスレッドモデルであるため、不要なコンテキストスイッチングとマルチスレッドの競合を回避でき、マルチスレッドスイッチングによる時間とパフォーマンスの消費を節約でき、シングルスレッドスイッチングを回避できます。デッドロックの問題を引き起こさない
  • 2.3 シングルスレッドを使用する理由
  • Redis はメモリ操作に基づいているため、ボトルネックになる可能性があるのはCPU
  • ではなく、
マシンのメモリまたはネットワーク帯域幅です。CPU がボトルネックではないため、シングルスレッド ソリューションを使用するのが自然です。さらに、マルチスレッドを使用するとさらに面倒です。ただし、Redis 4.0 では、バックグラウンド削除やその他の機能など

マルチスレッドのサポートが開始されました。 簡単に言えば、Redis 4.0 より前にシングル スレッドが使用されてきた主な理由は 3 つあります。

シングル スレッド モデルを使用すると、Redis の開発とメンテナンスが簡単になります。シングルスレッド モデルは開発とデバッグを容易にします。マルチスレッド モデルはいくつかの面ではうまく機能しますが、プログラムの実行順序に不確実性が生じ、同時読み取りと書き込みで一連の問題が発生し、システムの複雑さが増大し、スレッドの切り替え、ロックとロック解除、デッドロックによって引き起こされるパフォーマンスの低下。 RedisはAEイベントモデルやIO多重化などの技術により非常に高い処理性能を持っているため、マルチスレッドを使用する必要がありません。シングルスレッドメカニズムにより、Redis の内部実装の複雑さが大幅に軽減され、Hash の慣性、Rehash、Lpush およびその他の「スレッド安全でない」コマンドをロックなしで実行できます。

シングルスレッド モデルが使用されている場合でも、主に多重化およびノンブロッキング IO を使用して、複数のクライアント リクエストを同時に処理できます。 #Redis システムの場合、主な パフォーマンスのボトルネックは、CPU
ではなくメモリまたはネットワーク帯域幅です。

  • #3. Redis マルチスレッド モデル

  • ##3.1 マルチスレッドを導入する理由

  • シングルスレッドは非常に優れているのに、なぜマルチスレッドを導入するのでしょうか? シングルスレッドには、大きなキーの削除問題など、独自の問題もあります。 通常の状況では、del コマンドを使用してデータをすばやく削除できますが、削除されたキーが数千の要素を含むハッシュ セットなどの非常に大きなオブジェクトである場合、del コマンドにより Redis マスターが失敗します。行き詰まっています。

    そのため、Redis 4.0 では新しいマルチスレッド モジュールが追加されました。もちろん、このバージョンのマルチスレッドは主に、データ削除効率が比較的低いという問題を解決するためのものです。 lazy deletion を使用すると、Redis のラグの問題 (大規模なキーの削除など) を効果的に回避できます。手順は次のとおりです:

    • unlink key: DEL を使用する 同じキー削除関数の遅延なしの実装です. 唯一の違いは、UNLINK がセット タイプのキーを削除するときに、セット キーの要素数が 64 より大きい場合、メイン スレッドはキーの要素のみを削除することです。データベース辞書から削除するキーと実際のメモリ解放操作は別のバイオによって実行されます。要素の数が少ない場合 (64 未満)、または String 型の場合も、メイン スレッドで直接削除されます。

    • flushall/flushdb async: データベースのフラッシュ コマンド flashall/flushdb に、async 非同期クリーンアップ オプションが追加され、データベースのクリア時に Redis が非同期で動作するようになります。実装ロジックは、データベースに新しい空の辞書を作成し、元の古いデータベース辞書をバックグラウンド スレッドに渡して、データを 1 つずつ削除してメモリを解放します。

    • バックグラウンドの子プロセスに削除作業を処理して、データを非同期的に削除します。

    Redis は単一のメイン スレッド antirez によって処理されるため、 Redis の父は、常に「Lazy Redis の方が Redis より優れている」と強調してきました。

    lazy free の本質は、より高い削除によって 特定のコスト (メイン時間のレプリケーション、メインスレッドの CPU タイム スライスの占有) を削除することです。 Operations、redis より メインスレッドが取り除かれ、bio サブスレッドが処理できるようになり、メインスレッドのブロック時間が大幅に短縮されます。これにより、削除によって生じるパフォーマンスと安定性の問題が軽減されます。

    Redis 4.0 では、データの非同期遅延削除などの機能を実装するために複数のスレッドが導入されましたが、読み取りおよび書き込みリクエストを処理するスレッドは依然として 1 つしかないため、依然として狭義の単一スレッドとみなされます。

    前回の概要からの分析: Redis の主なパフォーマンスのボトルネックは、CPU ではなくメモリまたはネットワーク帯域幅です。メモリの問題は比較的簡単に解決できるため、Redis のボトルネックはネットワーク IO です。次に、マルチスレッド モデルを紹介します。

    3.2 マルチスレッドの動作原理

    I/O の読み取りと書き込み自体がブロックされます。ソケット、Redis データは呼び出しを通じてカーネル空間からユーザー空間にコピーされ、呼び出しのために Redis に渡されます。このコピー プロセスはブロックされています。データ量が多いと、コピーに時間がかかります。 、これらの操作は単一のスレッドに基づいて実行されます。

    Redis6 のシングルスレッド モデルとマルチスレッド モデルの簡単な分析

    Redis 6.0 では、I/O 読み取りおよび書き込みのパフォーマンスを向上させるために、新しい

    マルチスレッド関数が追加されました . 彼の主な実装アイデアは、IO 読み取りと書き込みを組み合わせることです。メインスレッドのタスクを独立したスレッドのグループに分割して実行できるため、複数のソケットの読み取りと書き込みを並列化できます。マルチチャネル I/O 多重化テクノロジの使用により、単一のスレッドで複数のタスクを効率的に処理できます。接続リクエスト (ネットワーク IO 時間の消費を最小限に抑える)、最も時間のかかるソケットの読み取り、リクエストの解析、書き込みは個別にアウトソーシングされ、残りのコマンドの実行は引き続きメイン スレッドによってシリアルに実行され、メモリ内のデータと対話します。 Redis6 のシングルスレッド モデルとマルチスレッド モデルの簡単な分析上の図と組み合わせると、
    ネットワーク データの読み取りと書き込み、およびリクエスト プロトコルの解析が複数の IO スレッドを通じて処理されることがわかります。実際のコマンドの実行には、メイン スレッドの操作が引き続き使用されます (スレッド安全性)、これは良い妥協点です。したがって、 は Redis 全体ではマルチスレッドですが、ワーカー スレッド (コマンド実行) では依然としてシングルスレッドです。

    3.3 ワークフロー

    コア プロセスは大まかに次のとおりです:

    Redis6 のシングルスレッド モデルとマルチスレッド モデルの簡単な分析プロセスは次のように簡単に説明されます:

      メイン スレッドは、ソケットを作成し、待機リストに入れます
    • ソケットを各 IO スレッドに割り当てます (リストがいっぱいになるまで待機しません)
    • メイン スレッド
    • ブロックして IO スレッドを待機します (マルチスレッド)ソケットの読み取りが完了しました
    • メインスレッド実行コマンド -
    • シングルスレッド (コマンドが受信されない場合は、次回の IO 継続を待ちます)
    • メインスレッド
    • IOスレッド待機中ブロック(マルチスレッド) ソケットへのデータの書き込みが完了しました(一度完了していない場合は、次回再度書き込まれます)
    • バインド解除と待機キューのクリア

    機能は次のとおりです:

    • IO スレッドは、同時にソケットを読み取っているか、同時に書き込みを行っており、同時に読み取りまたは書き込みを行うことはありません。
    • IO スレッドは、次のことのみを担当します。ソケット解析コマンドの読み取りと書き込みを行いますが、コマンド処理は担当しません (メインスレッドはコマンドをシリアルに実行します)
    • IO スレッドの数は自分で設定できます (現在のコード制限は 512##) #、デフォルトは 1 (この機能をオフにします))
    慎重に検討したストレス テストの結果、

    現在のパフォーマンスは 1 倍以上向上する可能性があります

    質問 1: 待機リストは常にブロックされ、満員でない場合は処理されませんか? 返信:
    ブロック時に検出されるのは、IO スレッドにまだタスクがあるかどうかです。処理が完了するまで待ってから続行してください。これらのタスクは実行中に追加されます。タスク数 これについてはまだ疑問が残っているのですが、誰か説明(コメント)してもらえませんか?

    3.4 マルチスレッドはデフォルトで有効ですか?

    Redis6.0 では、

    マルチスレッド メカニズムはデフォルトでオフになっています。マルチスレッド機能を使用する必要がある場合は、次の 2 つの手順を完了する必要があります。 redis.confの設定。 Redis6 のシングルスレッド モデルとマルチスレッド モデルの簡単な分析

      マルチスレッドを開始するには、io-thread-do-reads 構成項目を yes に設定します。
    • スレッド数を設定します。スレッド数の設定については、公式推奨では4コアCPUの場合はスレッド数を2または3に設定することを推奨しています。
    • 8コアCPUの場合は、スレッド数は 6 に設定することをお勧めします。スレッド数は、マシン コアとスレッドの数よりも少なくなければなりません。必ずしもマシン コアとスレッドの数が優れているわけではありません。

    4. 概要

    Redis 自体は、メモリ操作、シンプルなデータ構造、多重化およびノンブロッキング I/O に基づいて、デビュー以来優れています。回避 不要なスレッド コンテキストの切り替えやその他の機能が排除され、シングル スレッド環境でも依然として非常に高速です。

    ただし、ビッグ データのキーの削除は依然として非常に遅いため、マルチスレッドのリンク解除キー/フラッシュが必要でした。 Redis 4.0 で導入 async などのコマンドは主に Redis データの非同期削除に使用されます;

    I/O マルチスレッド読み取りおよび書き込みは Redis 6.0 で導入され、より多くのタスクをより効率的に処理できるようになりました。

    I/O の読み取りと書き込みをマルチスレッド に変えるだけで、 コマンドの実行は依然としてメインスレッド によってシリアルに実行されるため、マルチスレッド で Redis を動作させることはできません。スレッド セーフティの問題が発生しました

    Redis 元のシングルスレッド設計であっても、元の設計に反する現在のマルチスレッド設計であっても、目的は 1 つだけです。Redis をますます高速化することです。

    プログラミング関連の知識について詳しくは、

    プログラミング入門をご覧ください。 !

以上がRedis6 のシングルスレッド モデルとマルチスレッド モデルの簡単な分析の詳細内容です。詳細については、PHP 中国語 Web サイトの他の関連記事を参照してください。

声明:
この記事はjuejin.cnで複製されています。侵害がある場合は、admin@php.cn までご連絡ください。