我有以下(伪)代码:
static void ConvertBuffer( unsigned char * buffer, const int width )
{
#pragma omp parallel for
for ( int x = 0; x < width; ++x ) // one image row
{
RGB rgb = {0,0,0}; HSB hsb;
rgb.red = (float)buffer[x] / 255.;
RGBToHSB(rgb, hsb);
buffer[x] = hsb.brightness * 255;
}
}
这是一种非常天真的RGB→HSB转换算法实现。
第一个实现将一次拉出一条扫描线(=图像的一行),在我的情况下 65536字节。然而,在我的特定系统上进行试验和错误后,我发现我可以将总计算时间缩短 2 ,如果相反,我会一次处理 16 扫描线(= 1048576字节)。
我可以在运行时使用什么工具来猜测幻数,以便我不需要在代码中的某处硬编码16的神奇值?
如果我知道RGBToHSB
令人尴尬地并行且缓存友好,我是否可以完全填充L3 cache
并且应该接近最大可能的速度?
供参考,我的系统描述如下:
$ sudo likwid-topology
-------------------------------------------------------------
CPU type: Intel Core SandyBridge processor
*************************************************************
Hardware Thread Topology
*************************************************************
Sockets: 1
Cores per socket: 4
Threads per core: 1
-------------------------------------------------------------
HWThread Thread Core Socket
0 0 0 0
1 0 1 0
2 0 2 0
3 0 3 0
-------------------------------------------------------------
Socket 0: ( 0 1 2 3 )
-------------------------------------------------------------
*************************************************************
Cache Topology
*************************************************************
Level: 1
Size: 32 kB
Cache groups: ( 0 ) ( 1 ) ( 2 ) ( 3 )
-------------------------------------------------------------
Level: 2
Size: 256 kB
Cache groups: ( 0 ) ( 1 ) ( 2 ) ( 3 )
-------------------------------------------------------------
Level: 3
Size: 6 MB
Cache groups: ( 0 1 2 3 )
-------------------------------------------------------------
*************************************************************
NUMA Topology
*************************************************************
NUMA domains: 1
-------------------------------------------------------------
Domain 0:
Processors: 0 1 2 3
Relative distance to nodes: 10
Memory: 122.332 MB free of total 5898.17 MB
-------------------------------------------------------------
答案 0 :(得分:1)
你无法真正定义缓冲的'正确大小'。我的答案是尽可能地设置它。我会说介于10MB到100MB之间,但是如果你能负担得起它可以设置得更高,如果你的RAM不足则可以设置得更低。
如果您正在读取文件并写入文件(相同或其他),则应考虑使用内存映射文件。这样你就可以摆脱缓冲(由操作系统管理),你可以为整个图像调用你的函数一次。请注意,如果您的图像大于4GB,这在32位系统上可能不是一个好主意。