この記事では、Redis の有効期限戦略を紹介し、遅延削除戦略と定期削除戦略の実装方法を説明します。
Redis は各キーの有効期限を設定でき、各キーを有効期限とともに保存します。 set. を別の辞書に追加します。 [関連する推奨事項: Redis ビデオ チュートリアル ]
typedef struct redisDb { int id; //id是数据库序号,为0-15(默认Redis有16个数据库) long avg_ttl; //存储的数据库对象的平均ttl(time to live),用于统计 dict *dict; //存储数据库所有的key-value dict *expires; //存储key的过期时间 dict *blocking_keys;//blpop 存储阻塞key和客户端对象 dict *ready_keys;//阻塞后push 响应阻塞客户端 存储阻塞后push的key和客户端对象 dict *watched_keys;//存储watch监控的的key和客户端对象 } redisDb;
dict は、Redis データベースに含まれるすべての Key-Value キーと値のペアを維持するために使用され、expires は Redis データベース内の設定を維持するために使用されます。有効期限のキー (つまり、キーと有効期限のマッピング)。 ここでの有効期限はミリ秒のタイムスタンプで表現されていることに注意してください。たとえば、2022-01-02 22:45:02 に有効期限が切れる場合、値は 1641134702000
expire コマンドを使用する場合、有効期限に達すると、Redis はまず dict ディクショナリ テーブルを検索して、設定するキーが存在するかどうかを確認し、存在する場合は、キーと有効期限が Expires ディクショナリ テーブルに追加されます。
setex コマンドを使用してシステムにデータを挿入すると、Redis はまずキーと値をディクショナリ テーブルの辞書に追加し、次にキーを追加し、ディクショナリ テーブルの有効期限が切れます。 setex は文字列にのみ使用できることに注意してください。
簡単に言うと、有効期限が設定されたキーと特定の有効期限はすべて、expires ディクショナリ テーブルに保持されます。expire の使用法
expired コマンドは次のように使用します。expired key ttl (unit127.0.0.1:6379> expire name 2 #2秒失效 (integer) 1 127.0.0.1:6379> get name (nil) 127.0.0.1:6379> set name zhangfei OK 127.0.0.1:6379> ttl name #永久有效 (integer) -1 127.0.0.1:6379> expire name 30 #30秒失效 (integer) 1 127.0.0.1:6379> ttl name #还有24秒失效 (integer) 24 127.0.0.1:6379> ttl name #失效 (integer) -2Redis には、キーの有効期間 (キーが存続できる期間) または有効期限 (キーがいつ削除されるか) を設定するために使用できる 4 つの異なるコマンドがあります:expireコマンドを使用します。 キーの有効期間を ttl
秒に設定します。
pexpire コマンドを使用して、キーの有効期間を ttlミリ秒に設定します。キー key の有効期限を timestamp で指定された 秒 タイムスタンプに設定します。
pexpireat コマンドは、キー key の有効期限を timestamp # で指定された ミリ秒に設定するために使用されます。 ##タイムスタンプの数
expire、pexpire、およびexpiratの最終実装はすべてpexpireatによって実装されることに注意してください。つまり、クライアントによってどのコマンドが実行されても、Redisはそれをpexpireatコマンドに変換します。実行のために。したがって、expires ディクショナリに格納されている時刻は、ミリ秒のタイムスタンプで表されるキーの有効期限です。
有効期限ポリシー
キーの有効期限が切れた場合、いつ削除されますか?時間指定削除: キーの有効期限を設定する際に、キーの有効期限が切れたときにすぐに削除を実行できるようにタイマーを作成します。キー付属のキー削除操作です。 (
タイマー削除の作成)
利点
1.はい 最もメモリに優しい: タイマーを使用すると、期限切れのキーができるだけ早く削除され、占有されていたメモリが解放されます。利点
1. 最も CPU に優しい: キーは、キーが有効になった場合にのみ期限切れになります。削除されたキーはチェックされます。つまり、CPU を定期的にスキャンする必要がなく、多数のタイマーを作成する必要もありません。利点
1. 定期的な削除では、期限切れのキー操作が時々実行され、期間と頻度を制限することで削除操作による CPU 時間への影響が軽減されます。削除操作の影響。欠点 削除操作の期間と頻度を決定するのが困難です
1. 削除操作の実行頻度が高すぎるか、時間がかかりすぎる場合、定期的な削除戦略はスケジュールされた削除に変質し、CPU 実行時間が過度に消費されます。Redis は 2 つの戦略を使用します: 遅延削除 と 定期的な削除 : これら 2 つの戦略を適切に構成して使用します。この戦略により、サーバーは CPU 時間の合理的な使用とメモリ領域の無駄の回避との間で適切なバランスをとることができます。
遅延削除戦略の実装
期限切れキーの遅延削除戦略は、db.c/expireIfNeeded 関数によって実装されます。データベースの書き込み Redis コマンドが実行される前に、expireIfNeed 関数が呼び出され、入力キーがチェックされます。
コマンドは、次に示すように、expireIfNeeded 関数のプロセスを呼び出します。
さらに、アクセスされた各キーは削除される可能性があるため、各コマンド Both はキーの有無の両方を処理できなければなりません。 次の図は、get コマンドの実行プロセスを示しています。
定期削除戦略の実装
定期的期限切れのキーの有効期限 削除戦略は、redis.c/activeExpireCycle 関数によって実装されます。Redis サーバーが redis.c/serverCron 関数を定期的に実行するたびに、activeExpireCycle 関数が呼び出されます。この関数は、サーバー内の各データベースを 1 回の期間内に複数回走査します。指定された時間。
Redis は、デフォルトで 1 秒あたり 10 回の有効期限スキャンを実行します。有効期限スキャンは、有効期限ディクショナリ内のすべてのキーを走査するのではなく、単純な貪欲戦略を採用します。手順は次のとおりです。
(1) 期限切れの辞書からランダムに 20 個のキーを選択します。
(2) この 20 個のキーのうち、期限切れのキーを削除します。
(3) 期限切れのキーの割合が 1/4 を超える場合は、手順 (1) を繰り返します。同時に、期限切れのスキャンがオーバーサイクルしてプロセスがフリーズしないようにするために、アルゴリズムによりスキャン時間の上限も増加します。デフォルトでは 25 ミリ秒を超えません。
大規模な Redis インスタンス内のすべてのキーが同時に期限切れになったら、何が起こりますか?
CPU の消費
Redis 期限切れの辞書期限切れの辞書内の期限切れのキーがスパースになるまでスキャン (複数回ループ) が続けられ、その後停止します (ループの数が大幅に減少します)。
リクエストの遅延またはタイムアウトが発生する
クライアント リクエストが到着したときに、サーバーがたまたま期限切れのスキャン状態になった場合、クライアントのリクエストは少なくとも 25 ミリ秒待機することになります。処理中、クライアントがタイムアウト時間を 10 ミリ秒など比較的短く設定すると、タイムアウトにより多数の接続が閉じられ、ビジネス エンドで多くの例外が発生します。有効期限に必ず注意してください。多数のキーが期限切れになる場合は、有効期限にランダムな範囲を設定する必要があり、すべてのキーを同時に期限切れにすることはできません。
プログラミング関連の知識について詳しくは、プログラミング入門
をご覧ください。 !以上がRedis の有効期限戦略について説明する記事の詳細内容です。詳細については、PHP 中国語 Web サイトの他の関連記事を参照してください。