警告:函数 'Min' 的隐式声明在 C99 [-Wimplicit-function-declaration] 中无效

warning: implicit declaration of function 'Min' is invalid in C99 [-Wimplicit-function-declaration]

我遇到错误

警告:函数 'Min' 的隐式声明在 C99 中无效 [-Wimplicit-function-declaration]

当试图在不接触主输入的情况下从 3 个输入中找到最小值时。

#include <stdio.h>

void minVal (double x, double y, double z, double minVal)
{
    if (x<y && x<z)
        minVal = x;

    else if (y<x && y<z)
        minVal = y;

    else if (z<x && z<y)
        minVal = z;
}

int main(void) {
    double x, y, z, minVal;

    printf("Please enter three numeric values: ");
    scanf("%lf%lf%lf", &x, &y, &z);
    minVal = Min(x, y, z);
    printf("Min(%0.10f, %0.10f, %0.10f) = %0.10f\n", x, y, z, minVal);

    return 0;
}

正如消息所说,这是警告,不是错误。

您看到此消息是因为您正在调用未在任何地方声明的函数 Min。虽然编译会成功(带有警告),但链接可能会失败,因为 Min 也未定义。

您可能尝试调用的函数在您的代码中被命名为 minVal,而不是 Min

但是,您不能像现在这样从 main 调用 minVal,因为您还定义了一个名为 minVal 的局部变量,它隐藏了函数名称。要解决此问题,您必须重命名此变量:

double min;
...
min = minVal(x, y, z);

或者,重命名函数:

void Min(double x, double y, double z, double minVal)
...

这将导致更多错误:

  • 您的 minVal 函数没有 return 值(它的 return 类型是 void)。
  • 你的 minVal 函数有 4 个参数,而不是 3 个(但它忽略了第 4 个参数)。

最后一点值得进一步注意。在 C 函数中,参数是按值传递的,所以

f(x);

无法修改 x。类似地,在 minVal 中,最后一个参数(也被混淆地称为 minVal)只是该参数的本地副本,因此分配给它在函数之外没有任何效果。

您应该删除 minVal 参数并改为 return 一个值。

当你的老师点名 class 缺席的学生时,所有学生都可以大喊 "He isn't here!"

让我们看看警告:

warning: implicit declaration of function 'Min' is invalid in C99 [-Wimplicit-function-declaration]

这意味着,您正在尝试使用 Min 而未在您的代码中声明它,这是不允许的。 这不是错误,而是警告,最终会导致链接器错误。

这里:

minVal = Min(x, y, z);

因此,要么您需要编写一个名为 Min 的函数,要么您需要将 Min 替换为您已经声明的某个函数。例如,

void minVal (double x, double y, double z, double minVal)

现在,即使您将调用从 Min 更改为 minVal,它也不会起作用。因为您的代码有一个名为 minVal 的函数和一个同名变量。那是混乱的。养成避免使用相同名称声明变量和函数的习惯。

此函数正在 returning void,您正在尝试确定数据类型为 double 的 3 个输入中的最小值,并将该值分配给传递为一个论点。可行,但与 return 值相比不方便,对吧?

When trying to find the minimum value from 3 inputs without touching the main.

我建议这样:

#include <stdio.h>

double Min(double x, double y, double z)
{
    if (x<y && x<z)
        return x;
    else if (y<x && y<z)
        return y;
    else if (z<x && z<y)
        return z;
    else
        return 0.0;
}

int main(void)
{
    double x, y, z, minVal = 0.0;

    printf("Please enter three numeric values: ");
    scanf("%lf%lf%lf", &x, &y, &z);
    minVal = Min(x, y, z);
    printf("Min(%0.10f, %0.10f, %0.10f) = %0.10f\n", x, y, z, minVal);

    return 0;
}

此代码与您提出的代码相比有以下更改:

  • 函数从 minVal 重命名为 Min。请注意,通常首选使用 verbs/actions 作为函数名称,以便于解释函数的作用。因此,如果我可以自由更改 main() 函数,我将在所有地方(声明和函数调用)使用名称 Get_minValue 而不是 Min
  • Min 的 return 类型更改为 double,这样我就可以 return 值而不是将其分配给参数。

你仍然可以通过去掉 minVal 变量来让它变得更好,我会让你弄清楚:-)

此外,C99 是旧的,下次编译代码时,请确保使用 -std=c11 -pedantic-errors 编译它。

Here 您可以找到有关编译器选项的更多信息。

简单:C语言不允许调用未定义的函数(或宏)。这在 1999 年的 C 语言中有所改变,这就是为什么它说 "C99".

为了解决这个问题,您必须提供一个函数Min。就是这样。

您的问题已经得到正确回答,想对 void-function 的使用添加评论。

void minVal (double x, double y, double z, double minVal)

minVal 最有可能意味着 return 最小值。在这个只有一个 return 值的简单函数中,最佳选择确实是将您的代码更改为:

double minVal (double x, double y, double z, double minVal)

但是,如果您必须 return more 作为一个值,或者您必须 return 一个状态(例如输入两个或三个相等的数字)和一个值怎么办?然后你需要依靠引用调用。在 C 中,指针是要走的路。

void minVal (double x, double y, double z, double* min)
{
    if (x<y && x<z)
        *min = x;

    else if (y<x && y<z)
        *min = y;

    else if (z<x && z<y)
        *min = z;
}

int main(void) {
    double x, y, z, minValue;

    printf("Please enter three numeric values: ");
    scanf("%lf%lf%lf", &x, &y, &z);
    minVal(x, y, z, &minValue);
    printf("Min(%0.10f, %0.10f, %0.10f) = %0.10f\n", x, y, z, minValue);

return 0;
}

在这种情况下,使用 &minValue 将 minValue 的地址而不是 minValue 的值传递给 minVal 函数。 minVal函数中min表示将值存储到doublemin.

指向的地址