链接目标文件,包括多余?

时间:2010-11-01 17:02:06

标签: c linker compilation object-files

我正在尝试一下C。我以为我理解了这种联系业务。但我猜不是。我有一个简单的文件main.c:

#include "function.h"
int main(char args[])
{
    int print = myfunction();
}

然后是第二对文件function.c / function.h

int myfunction(); //function.h

int myfunction()  //function.c
{
    return 5;
}

编译这个很有用。但是,无论我是否在主文件中使用#include "function.h",它都能很好地工作。为什么我需要包含function.h呢?

5 个答案:

答案 0 :(得分:3)

我不知道你在使用什么系统,但如果它使用gcc或兼容的东西,请再次尝试

cc -Wall -Werror *.c

或者,打开系统的等效选项。

大型程序始终以这种方式构建,以便编译器检查参数类型。与动态和脚本语言不同,C生成实际的机器代码,并且不会在运行时检查参数计数或兼容性。

因此,函数原型被添加到基本语言中以在编译时进行类型检查。它们是可选的。

答案 1 :(得分:2)

C编译器不要求您在使用它之前为函数 1 指定原型。原型只是让编译器验证你传递的参数的类型是否符合函数所需的类型 - 并且如果它不正确则隐式转换为正确的类型,并且存在隐式转换从/到涉及的类型。

只要您的代码是完美的,并且您使用函数的方式与该函数的使用方式之间没有不匹配,您就不会有问题。在您的测试中,您有一个不带参数的函数,并返回一个int,而使用它的代码基本上没有其他任何东西。这种情况很难搞砸,而且效果很好。在具有数百或数千个函数的实际程序中,这些函数采用复杂类型的多个参数等,情况变化非常快。让编译器确保您正确调用函数变得更多更重要。

1 除了可变参数函数之外,甚至“变量”参数仍然基本遵循相同的规则,就好像没有函数的原型一样。

答案 2 :(得分:1)

当你使用一个尚未定义的函数时,许多C编译器只会假设它是一个返回int的extern函数(你经常会得到一个警告,但代码会编译。)当你遇到问题时你会遇到问题但是,开始使用具有更复杂参数和返回类型的函数。

答案 3 :(得分:0)

在头文件中声明一个函数,以便在不同的模块中使用它。您不一定需要源代码。您可以链接二进制库。在编译期间,您需要声明用于检查参数,类型等的方法。

在您的简单示例中,这不是必需的。

答案 4 :(得分:0)

如果使用尚未声明的函数,则较旧的C编译器将假定它具有参数...并返回类型int。不建议这样做。如果您打开编译器警告,您可能会收到有关使用未声明函数的警告。如果在编译main.c之前看到function.h,编译器可以捕获更多错误,因此它确切知道myfunction应该如何操作。