还是不懂
#include <iostream>using namespace std;int main(){ double a[2][3]= { {1,2,3}, {2,2,1} }; cout<<&a[0][0]<<endl; cout<<a[0]<<"\t"<<&a[0]<<endl; cout<<&a[0]<<"\t"<<a<<endl; cout<<a<<"\t"<<&a<<endl;}
#include <iostream>using namespace std;int main(){ double a[2][3]= { {1,2,3}, {2,2,1} }; cout<<&a[0][0]<<endl; cout<<a[0]<<"\t"<<&a[0]<<endl; cout<<&a[0]<<"\t"<<a<<endl; cout<<a<<"\t"<<&a<<endl; cout << typeid(&a[0][0]).name() << endl; // 输出double * cout << typeid(a[0]).name() << endl; // 输出double [3] cout << typeid(&a[0]).name() << endl; // 输出double (*)[3] cout << typeid(a).name() << endl; // 输出double [2][3]}
[解决办法]
它们的数据类型确实不一样,但这并不妨碍楼主问题的合理性。这一问题的关键是理解所谓的 array-to-pointer conversion,以及在何种情况下这种隐式转换会发生。cout 输出的时候会发生 array-to-pointer 的转换,转换的结果就是数组 a 的地址,这也是为什么所有输出结果都一样的原因。然而,c++ 标准要求参与 typeid operator 的表达式不发生 array-to-pointer 的隐式转换,所以会看到它们实际上类型不一样。但是把 typeid 扯进这个问题来造成了无意义的复杂化,因为这会导致为什么"不同类型的东西反而会必然有相同输出"的问题,1# 避重就轻的说"不同类型的东东没有比较意义",实际上回避了楼主本来的问题。
具体为什么 &a[0][0],&a[0],a[0],&a,a 在 cout 输出下都是相同的,是因为 array-to-pointer 不同程度的介入。
&a[0][0]:a[0][0] 为数组首元素,类型为 double,&a[0][0] 为其地址,即数组 a 地址。
&a[0]:a[0] 类型为 double[3] 的数组且其地址与数组 a 地址一样,&a[0] 取 a[0] 的指针,其值为 a[0] 的地址,而 a[0] 的地址又与 a 的地址相同,所以输出的还是数组 a 的地址。
a[0]:a[0] 仍然是 double[3] 且仍然具有与数组 a 一样的地址。问题是 cout 不知道如何输出数组,但这并没有引发编译错误,是因为 array-to-pointer conversion 介入了。编译器发现,虽然 cout 不知道如何输出 double[3] 的数组,但是 cout 知道如何输出 double(*)[3] 的指针,而 double[3] 到 double(*)[3] 又存在 array-to-pointer 的隐式转换,所以 cout 实际上输出的是经 array-to-pointer 转换过的 a[0],转换的结果即为 a[0] 的地址,即 &a[0]。
&a:这个显而易见了,就是取数组 a 的地址。
a:一样的逻辑,cout 不知道如何输出 double[2][3] 的数组类型,编译器使用了 array-to-pointer 的隐式转换,实际上输出的是 double(*)[2][3],即指向 a 的指针,其值即为数组 a 的地址。
最后声明一点,我和 1# 没有过节,对其回复的负面讨论纯属技术范畴。
[解决办法]
楼上有误 ,
链接
[解决办法]
看看楼上提供的链接。另外虽然你这里得到的地址都是一样,但是由于他们的类型不一致。比如
&a[0][0]的类型是double*而&a[0]的类型是double(*)[3]所以如果你都用double*来保存的话就会提示你编译问题