c - 解释这个 gcc 函数的类型化行为

标签 c types syntax function-pointers

在我的代码中,我必须使用多个函数作为lambda,例如您应该提供的qsort
因此,当我传递 int 类型的函数时,程序运行良好。但是当我添加另一个 double 类型的函数时,出现了错误消息:

1.c:44:29: error: invalid operands to binary < (have 'double *' and 'double')

从行:

return (*getter)(a) < target

其中 getter 是指向以下内容的指针:

double get_sex(struct human* a) { // it's the second function I've passed
    return a->sex;
}

我传递的两个函数之间的唯一区别是第一个是 int,第二个是 double

sometype somefunction (some parameters,
        int *comparator(struct human*, double, double *(struct human*)),
        double *getter(struct human*) ) {
    ....
}

我开始用 sizeof 检查它,发现代码 (*getter)(*a) 返回 4 个字节而不是 8 个字节,所以它一定是指针而不是 double 。这就是为什么我收到该错误消息的原因。 我去了Wikipedia举个例子,发现了额外的()。我已经添加了它们,现在它返回 8 个字节并且工作正常。

        double (*getter)(struct human*) ) {

所以问题是:为什么我应该在 getter 周围添加括号,而不是在 comparator 周围添加括号?函数返回 double 而不是 int 的原因是什么?!
这是我从未听说过的语法细节。

(我使用在 Windows 上已安装的编译器 – 来自 Perl 解释器 Strawberry)

最佳答案

你的问题来自于:

double *getter(struct human*)

隐式转换为:

double *(*getter)(struct human*)

这就是您收到错误的原因,因为您无法比较 (double *)double

您在使用 int 时不会遇到任何问题,因为您的指针 (int *) 已转换为 int 并且可以进行比较。但是,您的编译器应该警告您有关从指针到整数的隐式转换。

这里的问题是我从未见过可以用这种方式声明函数指针参数。我尝试编写一段代码,显然它有效。然而,这可能是 GCC 的一些非标准行为。定义函数指针的正确方法是使用括号。即

double (*getter)(struct human*)  /* 'getter' is a pointer to function taking
                                    struct human and returning double */

关于c - 解释这个 gcc 函数的类型化行为,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/13613256/

相关文章:

javascript - 执行 javascript 时不支持的返回类型

types - Hadoop 流式传输示例失败 映射中的键类型不匹配

php - 多种帖子类型的 WordPress 条件内容

java - Andrjoid JNI简单,接下来返回错误

c - 字符串末尾有奇怪的字符

c - 尝试将换行符添加到 char 数组的末尾时,strcat 不起作用

c - C中获取子网掩码

types - Rust函数签名和失效

c# - 在循环中获取每第 100 个值

c++ - C++ 中逗号运算符的语法使用