レイテンシーとは、あるシステムに何らかの入力を与え、それに対応する何らかの出力が出てくるまでの時間(遅延量)を指します。例えば、ある処理の実行を指令してから実際の結果が得られるまでに250ミリ秒かかったとすると、それは250ミリ秒のレイテンシーを持つシステムという事になります。それではここで、この時のスループットについて考えてみましょう。
以下の図は、横軸が時間で、250ミリ秒かけてある処理を4回実行した時の様子を示したものです。
上記の図に示した「ある処理」で取り扱われるデータが32MBだったと仮定します。このシステムの場合、「ある処理」を直列に実行しており、スループット[MB/s]は(32[MB] x 4) / 1[s] = 128[MB/s]となります。
さて、ハードウェアであってもソフトウェアであっても、最初に設計実装した処理のスループットが想定を下回り、結果的に何らかの対策が必要になる場合があります。必要なスループットに達していない場合、所望の処理を並列に実行する事でスループットを改善しますが、これは一体どのようなメカニズムによるものなのでしょうか?・・・というのが今日のお話。
さっそく先ほど1系統で行っていた処理を複数系統に拡張する事を考えてみます。下の図は、先ほどの処理を5並列で実行するようにしたものです。
上記の場合、スループット[MB/s] = ((32[MB] x 4 x 1) + (32[MB] x 3 x 4)) / 1[s] = 512[MB/s]となり、先ほどの128[MB/s]に対して大幅にスループットが向上している事がわかります。
直列的に処理する事になれた人が時間軸だけに注目してこの例を考えた場合、「250ミリ秒かかる処理なのに、どうして50ミリ秒毎に結果が出せるの?」と不思議に思うかもしれませんが、図示してみれば特別驚くべき事もありません。
このように、同じ処理を実行可能な系統を複数用意して並列動作させるだけで、システム全体のスループットを大幅に向上可能である事がわかります。上記の方法で重要な点のひとつは、系統毎の処理方法と処理時間は、系統を並列にする前の直列動作時と何ら変わりが無いという点です。
ここで、その他の方法として、単一の「ある処理」を複数に分割して、複数の系統で同時に並列処理する事も考えてみましょう。下記は、緑の部分は5つに分割して処理した結果、時間軸上では1/5の時間で済むことを示しています。
上記の場合、250ミリ秒かかる「ある処理」を5分割にして50ミリ秒ほどで完了する細かな処理に分割し、それら分割した処理を複数の系統で同時に処理する事で、レイテンシー50ミリ秒、計算系統5系統で「ある処理」を50ミリ秒で片づける事に設計する事になります。但し、並列化する前と後では、処理の実装が異なる他、並列化に要する新たなオーバーヘッドが発生する事があります。
システムにおけるレイテンシーとスループットを考える場合、何を並列化するのか、どのように並列化するのか、その並列化においてのスケーラビリティはどのようなものか、など様々な視点で設計について考察しなければなりません。
この話の続きには、同期と非同期や多段接続に関する話題、バッファリングに関する考察が必要ですが、それはまたの機会にと思います。