2013-07-19 47 views
2

我已经看到了回调这里几乎所有流行的问题,但仍然没有得到为什么回调,而不是通过正常的功能只是用来利用回调函数指针。这里是公认的答案(修改)的热门问题仍然没有得到回调与正常的函数调用

void populate_array(int *array, size_t arraySize, 
      int getNextValue(void)) // Note that, here I use normal function call. 
{ 
    for (size_t i=0; i<arraySize; i++) 
     array[i] = getNextValue(); 
} 

int getNextRandomValue(void) 
{ 
    return rand(); 
} 

int main(void) 
{ 
    int myarray[10]; 
    populate_array(myarray, 10, getNextRandomValue); 
    ... 
} 

正如你所看到的上面通过简单的函数,我依然可以实现回调实现的,那么为什么要使用函数指针来实现回调。 (即为什么通过参考),当我没有这个能做的时候。

此外,我们可以实现qsort, bsearch没有函数指针到他们提供的回调。那么,为什么要用指针功能的方式。

+0

他们俩的工作方式相同 - 他们是函数指针。类似于(在'main'的上下文中)'myarray'和'&myarray'都指向相同的事物。 –

+0

@DrewMcGowen几乎在那里。 “myarray”和“myarray”不指向相同的东西。 – 2013-07-19 15:10:54

+0

所以,为什么人们更喜欢'int(* foo)(void)'而不是'int foo()' –

回答

2
void populate_array(int *array, size_t arraySize, 
     int getNextValue(void)) // Note that, here I use normal function call. 

这不是一个函数调用:你不能在声明中有函数调用。 getNextValue是指向函数,它没有参数和使用不同的语法返回宣布为int

考虑这样比喻:你可以定义一个指针一个新的类型int和功能

typedef int* intptr_t; 
void myFunction(intptr_t ptr) { 
    ... 
} 

,或者你可以说,ptr是指向int的声明中的声明中使用它:

void myFunction(int* ptr) { 
    ... 
} 

以同样的方式,你可以在一个声明中使用它之前定义的函数指针类型

typedef void generator_t(void); 
void populate_array(int *array, size_t arraySize, generator_t getNextValue) { 
} 

,或者你可以说,getNextValue是使用从您的文章中替代语法的函数指针。

对函数指针使用typedef的一个原因是当你想要创建函数指针数组时需要进行一致性检查:如果你的库函数使用了在函数声明中定义的函数指针,那么你需要重新创建相同的声明在你自己的代码中创建一个你想要作为指针传递给库的指针数组。这可能会导致仅在调用库函数时才可见的不一致性,而不是数组声明的要点,这使得潜在问题难以追踪。

+0

那么,为什么这么做很困难,如果我们可以这样做 –

+0

@ ashish2expert我应该重复自己吗? “因为它更加明确,更接近事实。” – 2013-07-19 15:20:30

+0

@ ashish2expert在函数声明之外定义一个指针类型可以更容易地传递用于目标库内部的指针。 – dasblinkenlight

相关问题