float[]
OpenCL を使用して GPU 上の配列の縮小 (最小値と最大値を見つける) を行っています。
ワークグループごとに、いくつかの要素をメモリからglobal
メモリにロードしています。local
グローバル サイズがワークグループ サイズの倍数でない場合は、グローバル サイズの倍数になるように、グローバル サイズをパディングします。配列の終わりを過ぎた作業項目は、リダクションのニュートラル要素をlocal
メモリに入れます。
しかし、そのニュートラルな要素は何のためにあるべきmax()
でしょうか? 最大の機能?
OpenCL ドキュメントではMAXFLOAT
、HUGE_VALF
およびINFINITY
が非常に大きな正の (または符号なし)float
値として提供されます。ニュートラル要素を例にするのは理にかなっています-INFINITY
か?
現在HUGE_VALF
、中立要素としてを使用していますmin()
が、ドキュメントではそれHUGE_VALF
がエラー値として使用されているとも書かれているため、それは悪い考えかもしれません。
リダクション カーネル (コード):
#define NEUTRAL_ELEMENT HUGE_VALF
#define REDUCTION_OP min
__kernel void reduce(__global float* weights,
__local float* weights_cached
)
{
unsigned int id = get_global_id(0);
// Load data
if (id < {{ point_count }}) {
weights_cached[get_local_id(0)] = weights[id];
} else {
weights_cached[get_local_id(0)] = NEUTRAL_ELEMENT;
}
barrier(CLK_LOCAL_MEM_FENCE);
// Reduce
for(unsigned int stride = get_local_size(0) / 2; stride >= 1; stride /= 2) {
if (get_local_id(0) < stride) {
weights_cached[get_local_id(0)] = REDUCTION_OP(weights_cached[get_local_id(0)], weights_cached[get_local_id(0) + stride]);
barrier(CLK_LOCAL_MEM_FENCE);
}
// Save
weights[get_group_id(0)] = weights_cached[0];
}
編集:
私は実際にニュートラル要素としてfmin()
and をfmax()
一緒に使用することになりました-数値が常に返されるため、これは基本的にOpenCLドキュメントNAN
に従って動作することが保証されています( は2つの値が指定された場合にのみ返されます)。NAN
NAN