作者sbrhsieh (sbr)
看板C_and_CPP
标题Re: [问题] 原来这样写是没意义的
时间Thu Apr 23 16:31:02 2009
※ 引述《QQ29 (我爱阿蓉)》之铭言:
: 我一直以为
: 对一个静态阵列取sizeof 一定可以...
: 但我刚刚才发现
: double pp[20];
: init(pp);
: void init(double array[])
: {
: cout<<sizeof(array);
: }
: 原来副程式取 怎麽样都还是印4
: 所以说 其实传递array 用 array接
: 根本也跟用*ptr去接是一样的?? 也都是call by value 复制他的记忆体位置(值)
: 让array指到我的pp ,这样说对嘛?
: 现在才发现这样= = 不过这是否意味 根本无法利用副程式 去取得
void init(double array[]) 中 formal paratemer array 的语意与
void init(double* array) 中的 array 相同。
但是这不意味着 function 的 formal parameter 不能是 array pointer/reference。
你是可以让 formal parameter 带有 array length 的资讯,但因为宣告 array type
的变数时 array length 必须是编译期常数,所以当 formal parameter 是 array
type 的 pointer/reference,实际上是限制了能够 pass 到 function 的 array
种类(就 array length 来说,相同 element type 但 length 不同视为不同 array)。
using namespace std;
void init(double (*p)[20])
{
int n = sizeof(*p) / sizeof((*p)[0]);
cout << "initialize a double array with length " << n
<< ", total bytes: " << sizeof(*p) << endl;
for (int i = 0; i < n; ++i)
cout << "array[" << i << "]=" << (*p)[i] << endl;
}
如果写出这样的码,你可能会说 1.这样子的码计算 n 的部分没什麽意思,因为我在
编译期就知道 n 的值;2. 而且也限制了能够交由 init function 处理的 array 种类。
关於第一点的确是这样,这样子写只是强调 formal parameter type 在编译期的确
带有 array length 资讯(不过这可能不需要强调,C programmer 应该都有这样的
sense)。
你可以透过另一位板友将 init 样版化的作法来增加使用上的弹性,他等於是让
编译器帮你产生多个类似 init function 实做的个别 function 来应付各种
element type 与各种 array length 的 argument。
至於第二点,如果单就只存在一个 init function 的情况来说(不使用样版扩展),
他实际上还是可以用来处理至少有 20 个 double 并排的空间大小的空间,由於
C/C++ 语言的 casting 语法/机制让程式员可以变更编译期型别资讯。
int main()
{
double a[20];
for (int i = 0; i < 20; ++i)
a[i] = i;
init(&a);
double b[30];
for (int i = 0; i < 30; ++i)
b[i] = 30 - i;
init(reinterpret_cast<double (*)[20]>(b + 10));
}
通常如果想要设计一个单一 function 可以处理特定 element type 但不定长度
的 array(区块),又不想明确传递长度资讯,会采用类似 c str 的作法,使用一个
不代表有效值的 value 放在 array 最後(sentinel)。
--
※ 发信站: 批踢踢实业坊(ptt.cc)
◆ From: 218.173.134.233
※ 编辑: sbrhsieh 来自: 218.173.134.233 (04/23 16:33)
※ 编辑: sbrhsieh 来自: 218.173.134.233 (04/23 16:51)
1F:推 QQ29:谢谢你的解说 受益良多 04/24 02:06