我开始使用C编程。我目前有一个包含很多功能的大文件。我想将这些函数移动到一个单独的文件,以便代码更容易阅读。但是,我似乎无法弄清楚如何正确包含/编译,并且无法在我找到的任何在线教程中找到示例。这是一个简化的例子:
#include <stdlib.h>
#include <stdio.h>
void func1(void) {
printf("Function 1!\n");
}
void func2(void) {
printf("Function 2!\n");
}
int main(void) {
func1();
func2();
return 0;
}
如何将C函数移动到单独的文件中?仅供参考:我正在使用gcc。
更新:这些答案非常有用,谢谢。现在似乎我的简化示例不够好,因为我意识到我的程序编译失败的原因是因为我在我的函数中使用了一个全局变量。
#include <stdlib.h>
#include <stdio.h>
int counter = 0;
void func1(void) {
printf("Function 1!\n");
counter++;
}
int main(void) {
func1();
return 0;
}
将这些函数移动到外部文件不起作用,因为它们需要引用此全局变量:
#include <stdlib.h>
#include <stdio.h>
#include "functions.c"
int counter = 0;
int main(void) {
func1();
counter = 100;
return 0;
}
如何解决这个问题?
答案 0 :(得分:23)
好。我们走了。
您的 main.c 文件
#include <stdlib.h>
#include <stdio.h>
#include "functions.h"
int main(void) {
func1();
func2();
return 0;
}
您的 functions.h 文件
void func1(void);
void func2(void);
您的 functions.c 文件
#include "functions.h"
void func1(void) {
printf("Function 1!\n");
}
void func2(void) {
printf("Function 2!\n");
}
用以下内容编译:
gcc -o main.exe main.c functions.c
答案 1 :(得分:8)
最常见的方法是将函数原型放在头文件中,将函数实现放在源文件中。例如:
func1.h
#ifndef MY_FUNC1_H
#define MY_FUNC1_H
#include <stdio.h>
// declares a variable
extern int var1;
// declares a function
void func1(void);
#endif
func1.c
#include "func1.h"
// defines a variable
int var1 = 512;
// defines a function
void func1(void) {
printf("Function 1!\n");
}
func2.h:
#ifndef MY_FUNC2_H
#define MY_FUNC2_H
#include <stdio.h>
void func2(void);
#endif
func2.c:
#include "func1.h" // included in order to use var1
#include "func2.h"
void func2(void) {
printf("Function 2 with var1 == %i\n", var1);
}
main.c中:
#include <stdio.h>
#include "func1.h"
#include "func2.h"
int main(void) {
var1 += 512;
func1();
func2();
return 0;
}
然后使用以下内容进行编译:
gcc -c -o func1.o func1.c
gcc -c -o func2.o func2.c
gcc -c -o main.o main.c
gcc -o myprog main.o func1.o func2.o
./myprog
我只在每个源/标题对中放置了一个函数用于说明。您可以只创建一个包含所有源文件原型的标头,也可以为每个源文件创建多个标头文件。关键是任何调用该函数的源文件都需要包含一个包含该函数原型的头文件。
作为一般规则,您只需要包含一次头文件,这是头文件中#ifndef #define #endif
宏的用途。
答案 2 :(得分:4)
首先,您必须了解声明和定义之间的区别。声明告诉编译器存在某些东西,如函数。对于函数的情况,定义是实际的函数实现。
所以你要做的是将定义移动到另一个文件,但是在要调用函数的文件中添加一个声明。然后,您将这两个文件一起构建,编译器和链接器将负责其余的工作。
答案 3 :(得分:-1)
你可以创建两个文件:一个带有main函数,另一个带有其余文件。
如果您在另一个文件中的函数使用来自另一个模块/文件的全局变量,则需要在模块中的全局变量声明前面添加“extern”和函数定义。这告诉编译器您正在从另一个文件访问全局变量。
以下是定义全局变量“x”并在main.c文件中调用函数“myfunction”的示例。“myfunction”在functions.c文件中定义。“x”还需要在functions.c文件中声明,但由于它将从另一个文件访问“x”,它需要在它前面有一个“extern”。“myfunction”取外部全局变量“x”,将其递增1并将其打印出来。请考虑以下代码:
main.c看起来像是:
#include <stdio.h>
#include "functions.c"
int x = 1;
int main()
{
myfunction();
printf("The value of x in main is: %d\n", x);
return(0);
}
functions.c将类似于:
#include <stdio.h>
extern int x;
void myfunction(void)
{
x++;
printf("The value of x in myfunction is: %d\n",x);
}
请注意,main.c使用“int x;”声明x,而functions.c使用“extern int x”来声明x。
要编译代码,请确保两个文件位于同一文件夹中,并且就像只有一个文件一样编译。例如,如果在linux系统和gcc上使用gcc,则命令行输入将如下所示:
gcc main.c -o main
./main
第一行编译代码,第二行运行代码。输出应如下所示:
myfunction中x的值为:2 main中x的值为:2
请注意,“x”的值也在main中更改,因为“x”是全局变量。
答案 4 :(得分:-2)
你可以这样做。
/* func1.c */
void func1(void) {
printf("Function 1!\n");
}
/* func2.c */
void func2(void) {
printf("Function 2!\n");
}
/* main.c */
#include "func1.c"
#include "func2.c"
int main ( void )
{
func1();
func2();
return 0;
}