後で適応しきい値処理ルーチンで使用するために、合計面積テーブルを作成しようとしています。このコードはタイム クリティカルなソフトウェアで使用されるため、コードからできるだけ多くのサイクルを絞り出そうとしています。
パフォーマンスのために、テーブルはすべてのピクセルの符号なし整数です。
プロファイラーをアタッチすると、x-pass の実行時にパフォーマンスの最大のボトルネックが発生することがわかります。
計算の簡単な数式は次のとおりです。
sat_[y * width + x] = sat_[y * width + x - 1] + buff_[y * width + x]
where the running sum resets at every new y position.
この場合、sat_
は SAT を表す符号なし整数の 1 次元ポインタでbuff_
あり、8 ビットの符号なしモノクロ バッファです。
私の実装は次のようになります。
uint *pSat = sat_;
char *pBuff = buff_;
for (size_t y = 0; y < height; ++y, pSat += width, pBuff += width)
{
uint curr = 0;
for (uint x = 0; x < width; x += 4)
{
pSat[x + 0] = curr += pBuff[x + 0];
pSat[x + 1] = curr += pBuff[x + 1];
pSat[x + 2] = curr += pBuff[x + 2];
pSat[x + 3] = curr += pBuff[x + 3];
}
}
私のコンパイラ(VC11)が私のためにそれをしなかったので、ループは手動で展開されます。私が抱えている問題は、セグメンテーション ルーチン全体がそのループを実行するだけで非常に長い時間を費やしていることです。何がそれを高速化できるかについて誰か考えているかどうか疑問に思っています。私は SSE のすべてのセットと、このルーチンが実行される任意のマシンの AVX にアクセスできるので、そこに何かがあれば非常に便利です。
また、最後のサイクルを絞り出したら、これをマルチコアに拡張する予定ですが、モデルをより複雑にする前に、シングル スレッドの計算をできるだけ厳密にしたいと考えています。