速度增益:将2D阵列转换为1D阵列

时间:2014-04-18 07:43:31

标签: c++ arrays performance multidimensional-array

我最初有一个2D阵列。结果需要时间来取回结果。所以,我将2D数组转换为1D数组,但我的程序速度仍然没有太大改善。

这是我的代码:

for( counter1=0; counter1< size ; ++counter1)
    {   
       y=buffer[counter1];
       x=buffer[counter1+1];

       IndexEntries index= OneDTable[x*256+y];

    SingleTableEntries NewNextState=NewSingleTable[Next*blocksize+index];

    Next=NewNextState.Next_State;
    if(NewNextState.accept[index.serialnumber]=='1' )
    {
        return 1;           
    }

}

在上面的代码中:OneDTable是从256 * 256个元素的2D数组生成的一维数组。 NewSingleTable是一个2D阵列的块大小*(下一个元素总数)生成的一维数组。

实际上,在转换成1D阵列后,我预计会有很大的速度提升。这是从一维数组中提取值的正确方法,还是可以对上面的代码进行某些改进?

更多详情:

两个2D数组都是结构类型:

Structure type of IndexEntries consists of:
          int  
          int

Structure type of NewSingleTable consists of:
          int
          vector<char>

1 个答案:

答案 0 :(得分:2)

你可以获得从矢量向量到普通向量的变化。例如。从:

std::vector<std::vector<my_struct>> table(total_rows,
                                          std::vector<my_struct>(total_columns,
                                                                 my_struct()));

// do something with table[row][column]...

std::vector<my_struct> table(total_rows * total_columns);

// do something with table[row * total_columns + column]...

这是因为vector of vector is not really a matrix and you lose data locality

改变自:

my_struct table[total_rows][total_columns];

my_struct table[total_rows * total_columns];

是没有价值的,因为两者之间的内存布局(通常)完全相同。

唯一的区别是数组的语义类型以及您现在必须自己实现2D元素查找的事实(当然从table[row * 256 + column]更改为table[row << 8 + column]是没有用的,因为任何体面的编译器都会自动执行此操作&#34;优化&#34;)。

当您必须对每个元素执行操作时,1D数组可能会更快一些。这是因为循环更简单:

for (unsigned row(0); row < total_rows; ++row)
  for (unsigned column(0); column < total_columns; ++column)
    // do something with table[row][column]

const unsigned stop(total_rows * total_columns);
for (unsigned i(0); i < stop; ++i)
  // do something with table[i]

但这不是你的情况。

正如laune所说的是评论,复制一个NewSingleTable只是为了提取几个整数是不好的

SingleTableEntries NewNextState=NewSingleTable[Next*blocksize+index];

从你的例子中看来,const引用应该足够了:

...
const SingleTableEntries &NewNextState(NewSingleTable[Next * blocksize + index]);

if (NewNextState.accept[index.serialnumber] == '1' )
  return 1;           

Next = NewNextState.Next_State;
...