Bjarne Stroustrup在他的《C++ 编程语言》一书中提到(C.7.2;特别版的第 838 页,2000):
...我们可以这样初始化ma
:
void int_ma() {
for(int i=0; i<3; i++)
for(int j=0; j<5; j++) ma[i][j] = 10 * i + j; }
...
该数组ma
只是int
我们访问的 15 s,就好像它是 3 个 5 int
s 的数组一样。特别是,内存中没有单个对象是矩阵ma
- 只有元素被存储。维度 3 和 5 仅存在于编译器源代码中。
(强调我的)。
换句话说,符号[][]...[]
是编译器构造;如果你愿意的话,语法糖。
出于娱乐目的,我编写了以下代码:
#include<cstdlib>
#include<iostream>
#include<iterator>
#include<algorithm>
int main() {
double ma[5][3]; double *beg = &ma[0][0]; // case 1
//double ma[3][5]; double *beg = &ma[0][0]; // case 2
//double ma[15]; double *beg = &ma[0]; // case 3
double *end = beg + 15;
// fill array with random numbers
std::generate(beg, end, std::rand);
// display array contents
std::copy(beg, end, std::ostream_iterator<double>(std::cout, " "));
std::cout<<std::endl;
return 0;
}
并使用编译命令(GCC 4.7.2)比较了三种情况生成的程序集:
g++ test.cpp -O3 -S -oc1.s
这些情况称为c1.s
、c2.s
和c3.s
。该命令的输出shasum *.s
是:
5360e2438aebea682d88277da69c88a3f4af10f3 c1.s
5360e2438aebea682d88277da69c88a3f4af10f3 c2.s
5360e2438aebea682d88277da69c88a3f4af10f3 c3.s
现在不得不提一下,最自然的构造似乎是 的一维声明ma
,即:double ma[N]
,因为那么初始位置是简单ma
的,而最终位置是简单的ma + N
(这与取第一个的地址相反)数组元素)。
我发现<algorithm>
C++ 标准库头文件提供的算法更适合这种情况。
最后,我必须鼓励您考虑使用std::array
orstd::vector
如果可能的话。
干杯。