A nice tutorial on function pointers举了一个例子,我有一个问题。这是一个简单的排序函数,它有一个函数作为其参数之一。这是函数调用。正如您所看到的,(* compar)函数有两个“const void *”争论
void qsort(void *base, size_t nmemb, size_t size,
int(*compar)(const void *, const void *));
稍后会调用此函数:
#include <stdlib.h>
int int_sorter( const void *first_arg, const void *second_arg )
{
int first = *(int*)first_arg;
int second = *(int*)second_arg;
if ( first < second )
{
return -1;
}
else if ( first == second )
{
return 0;
}
else
{
return 1;
}
}
int main()
{
int array[10];
int i;
/* fill array */
for ( i = 0; i < 10; ++i )
{
array[ i ] = 10 - i;
}
qsort( array, 10 , sizeof( int ), int_sorter );
for ( i = 0; i < 10; ++i )
{
printf ( "%d\n" ,array[ i ] );
}
}
我的问题是编译器如何知道“int_sorter”正在比较哪两个元素?它们在初始函数中没有被调用,我认为这是因为作为参数调用的函数处理了这个问题,但 函数如何知道在这个数组中我们正在比较这些两个数字?
我也不确定*(int *)
是什么意思;我怀疑这是答案的一部分。
答案 0 :(得分:3)
qsort()
函数负责(重复)使用正确的两个指针调用比较器函数。它们是指向传递给qsort()
的数组的两个元素的指针。编译器不知道哪两个元素int_sorter()
正在比较。
first = *(int *)first_arg;
符号将const void *
转换为int *
,然后取消引用int
(读取它,因此不违反const
约束),以及将值分配给first
。 const void *
参数说“比较器函数不应该修改指针参数指向的数据”。
qsort()
的设计允许它对任何类型的数组进行排序;它所需的信息都存在于界面中。
答案 1 :(得分:2)
我的问题是编译器如何知道哪些元素 “int_sorter”正在比较?它们在初始函数中没有被调用 我认为这是因为被称为参数的函数处理
是的,确切地说。 qsort()
函数使用您给它的函数指针(指向int_sorter
的)来调用函数int_sorter
。它通常会多次调用int_sorter
,每次都要使用数组中的不同元素进行排序。
但是这个函数如何知道我们在这个数组中 比较这两个数字?
同样,该功能本身并不知道。 qsort()
函数决定它必须比较哪些数字,然后比较它们。
如果你看一个sort函数的简单实现,它可能会有所帮助,所以你可以看到实际的函数调用。
我也不确定*(int *)是什么意思
正如在另一个答案中所解释的那样:(int*)
表示“将其强制转换为'指向int'的指针”。前面的星是解除引用的运算符(从指针到值)。