假设我们有以下函数(在C中):
int sum(int a, int b){
return a+b;
}
int diff(int a, int b){
return a-b;
}
所以我们知道我们可以通过以下方式声明一个函数指针数组:
int (*test[2]) (int a, int b);
test[0] = sum;
test[1] = diff;
但以下内容也有效(但我们使用堆分配):
int (**test) (int a, int b) = malloc( 2*sizeof(*test));
test[0] = sum;
test[1] = diff;
到目前为止一切顺利。现在让我们记住,我们可以做一个(动态分配的)两个整数的数组:
int* test = malloc( 2*sizeof(int));
那么为什么我们不能将函数指针数组声明为
int (*test) (int a, int b) = malloc( 2*sizeof(*test)); ?
是因为测试与*test
和**test
相同(等等),malloc( 2*sizeof(*test))
返回指向函数指针的指针,因此它不能被分配到(*test)
?
如果这个假设是正确的,你可以用详细解释解释为什么我们得到编译错误
error: lvalue required as left operand of assignment
当我们尝试做的时候
int (*test) (int a, int b) = malloc( 2*sizeof(*test));
test=diff; //<--- This is ok.
test+1 = sum; //<--- This is what gives the error!
免责声明:我认为这是一个基本问题而且假设是正确的,但我想要一个更好的解释,让这种事情一劳永逸地清楚。
编辑:
请注意,这相当于
int (*test) (int a, int b) = malloc( 2*sizeof(*test));
*test=*diff; //<--- This is ok.
*(test+1) = *sum; //<--- This is what gives the error!
因为这与案件有点相似:
int *test = malloc(2*sizeof(*test));
*test = 0;
*(test+1) = 1;
答案 0 :(得分:11)
那么为什么我们不能将函数指针数组声明为
int (*test) (int a, int b) = malloc( 2*sizeof(*test));
因为test
没有指向函数指针; 是一个函数指针。因此,它不能指向函数指针数组的第一个元素。
如果需要函数指针数组,请使用上一个表单:
int (**test) (int a, int b) = malloc( 2*sizeof(*test));
这里,*test
具有函数指针类型,因此test
可以(并且确实)指向函数指针数组的第一个元素。进一步:
error: lvalue required as left operand of assignment
当我们尝试做的时候
int (*test) (int a, int b) = malloc( 2*sizeof(*test)); test=diff; //<--- This is ok. test+1 = sum; //<--- This is what gives the error!
无论test
具有什么类型,test+1=anything
始终无效C. test+1
永远不能是左值。我不明白你为什么会这样做。
GCC还在报道你的计划中的另一个错误sizeof(*test)
。由于*test
具有函数类型,sizeof(*test)
无效,但GCC默默地为其赋值1.这导致为函数指针分配的内存太少,但无论如何都无关紧要,因为在下面你抛弃从malloc
得到的记忆并将其他东西分配给test
。