如何加速指针解引用?

4

这是我的代码:

#include <stdlib.h> //malloc

#define lineSize 16
#define columnSize 16
#define cellSize 16

int main()
{
    unsigned char*** tab;
    tab = malloc(sizeof(unsigned char**) * lineSize);
    for(unsigned int i = 0; i < lineSize; i++)
        tab[i] = malloc(sizeof(unsigned char*) * columnSize);
    for(unsigned int i = 0; i < lineSize; i++)
        for(unsigned int j = 0; j < columnSize; j++)
            tab[i][j] = malloc(sizeof(unsigned char) * cellSize);


    unsigned int line = 0;
    unsigned int column = 0;
    unsigned int cell = 0;

    unsigned char* ptr = &tab[line][column][cell];

    for(line = 0; line < lineSize; line++)
        for(column = 0; column < columnSize; column++)
            for(cell = 0; cell < cellSize; cell++)
                *ptr = ...;

    return 0;
}

这段代码会用在运行时才能确定的值来填充表格。
当lineSize、columnSize和cellSize较小时,没有太多问题。但是,当cellSize变成100000以上时,指针解引用的时间成本就变得很高了。因此,我考虑使用指针来避免解引用。
问题是,我不知道如何更新指针,以便跟随line、column或cell的更改而更新。
感谢您的帮助,谢谢。
编辑:更多解释:
随着lineSize、columnSize和cellSize越来越大,执行时间越长是可以预料的。但是,在循环内部花费了很多时间,而在循环内部,指针被解引用了16*16*100000次(当cellSize=100000时)。
如果我没错的话,解引用就像乘法一样:
tab[2][5][3] = tab + 2*16*100000 + 5*100000 + 3;

而像16*16*100000 这样的数学计算会很费时间。

所以为了避免这种计算,我想到了一个指针,它永久指向tab[line][column][cell],但我不知道如何在cell增加时不必每次重新计算指针。


为什么你不把地址的确定(即写入指针变量)放到循环中呢?如果你通过该指针多次访问,它可以节省时间。如果你没有这样做,那么引入指针是朝错误的方向迈出的一步。直接访问 tab[line][column][cell] 一两次即可。 - Yunnosch
@Yunnosch 将指针地址的决定直接移动到循环中不会有所帮助。它将做完全相同数量的计算,就好像我只是使用了 tab[line][column][cell] - Tom Clabault
这只对单个访问有效。实际上,首先存储指针的成本更高。所以就像我说的那样,是朝错误的方向迈出的一步。 - Yunnosch
你可以选择冒险的方式,即通过增加指针的差值(根据你的某种适当的数学计算)来实现。但是,这里有风险。 - Yunnosch
@Yunnosch 我会测试一下。 - Tom Clabault
显示剩余13条评论
2个回答

3

使用3维数组时,除了最后一维以外,您不能将指针移动到新位置。您可以沿着cell维度移动ptr,但不能沿着其他维度移动。

要做到这一点,只需添加距离:

ptr2 = ptr + dist

您在编辑中提到的计算与解引用不同,它们是在将1-D数组解释为3-D数组时使用的。这将允许沿所有维度移动。


您可以执行以下操作:

for(line = 0; line < lineSize; line++) {
    unsigned char** my_line = tab[line];
    for(column = 0; column < columnSize; column++)
        unsigned char* my_col = my_line[column];
        for(cell = 0; cell < cellSize; cell++)
            unsigned char data = my_col[cell];

-1

你的代码中存在未定义行为(UB)。

tab[line][column][cell]; 

不适用于单独分配的值。它仅适用于连续的内存块,容纳所有表元素的数组。您的内存块可以位于任何位置。


2
并不是 tab[line][column][cell] 不能工作,而是问题在于你无法像处理连续块一样在顶部进行操作并移动指针。 (虽然我没有给你点踩,但我理解你的意思,只是我认为第一句话可能会让人感到困惑) - vgru

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接