编写一个由头文件greeting.h、自定义函数文件greeting.c、主函数文件myapp.c 构成的c 程序,并根据这三个文件的依赖关系编写makefile 文件
时间: 2023-05-31 08:20:20 浏览: 250
### 回答1:
这段话描述的是一个由头文件 greeting.h、自定义函数文件 greeting.c 和主函数文件 myapp.c 构成的 C 程序,同时还需要编写一个 makefile 文件来实现这三个文件的依赖关系编译。
### 回答2:
C语言程序的结构一般包括头文件、源文件和可执行文件。其中头文件用于声明函数和类型,源文件包含函数的实现,可执行文件是通过链接各个源文件生成的二进制文件。为了方便管理和编译,我们需要使用makefile文件来自动化编译和链接过程。下面介绍如何编写一个由头文件greeting.h、自定义函数文件greeting.c、主函数文件myapp.c构成的C程序,并编写makefile文件。
首先是头文件greeting.h。这个头文件应该声明程序中用到的所有函数和类型。我们假设程序中需要两个函数:greeting和byebye,以及一个结构体类型person。
下面是greeting.h文件的内容:
```
#ifndef _GREETING_H_
#define _GREETING_H_
typedef struct {
char name[20];
int age;
} person;
void greeting(person* p);
void byebye();
#endif
```
接下来是自定义函数文件greeting.c。这个文件包含程序中声明的所有函数的实现。在这个文件中,我们实现了greeting和byebye两个函数。
下面是greeting.c文件的内容:
```
#include <stdio.h>
#include "greeting.h"
void greeting(person* p)
{
printf("Hello, %s! You are %d years old.\n", p->name, p->age);
}
void byebye()
{
printf("Goodbye!\n");
}
```
最后是主函数文件myapp.c。这个文件包含程序的主函数main,在这个函数中我们创建了一个person结构体,调用了greeting函数,然后调用byebye函数结束程序。
下面是myapp.c文件的内容:
```
#include <stdio.h>
#include "greeting.h"
int main()
{
person p = {"Alice", 20};
greeting(&p);
byebye();
return 0;
}
```
现在我们需要编写makefile文件来将这三个文件编译和链接成一个可执行文件。makefile文件中需要指定编译器和各个源文件的依赖关系。为了简化代码,这里我们使用gcc编译器。
下面是makefile文件的内容:
```
CC=gcc
SRCS=myapp.c greeting.c
OBJS=$(SRCS:.c=.o)
all: myapp
myapp: $(OBJS)
$(CC) -o $@ $^
%.o: %.c greeting.h
$(CC) -c $<
clean:
rm -f $(OBJS) myapp
```
在这个makefile文件中,CC变量指定了使用的编译器,SRCS变量指定了所有的源文件,OBJS变量是将所有源文件用于生成的目标文件,all是默认目标,它将会生成可执行文件myapp。如你所见,这个makefile文件包含了三个目标:all、myapp和clean。其中,all和myapp都是生成可执行文件的目标,clean是清除中间文件的目标。生成可执行文件需要执行两个步骤:先将每个源文件编译成目标文件,然后将所有目标文件链接起来形成可执行文件。makefile中的规则通过依赖关系指定了对象文件和源文件之间的关系,也指定了要使用的编译器和编译选项。注意到我们还规定了生成每个目标文件的规则,它依赖于对应的源文件和头文件。最后,我们提供了一个用于清除中间文件的规则clean。这个规则将会删除所有目标文件和可执行文件。
现在,用指令make即可生成可执行文件myapp。当然,在makefile中指定的编译器和生成的可执行文件名称等可以根据需要进行调整。
### 回答3:
将程序分为头文件、函数文件及主函数文件,能够更好地提高程序的可读性和拓展性。下面是关于如何编写由头文件greeting.h、自定义函数文件greeting.c、主函数文件myapp.c构成的c程序的具体步骤:
首先创建greeting.h头文件,以便为其他文件提供外部函数的声明和常量的定义。头文件的定义如下:
```
// greeting.h
#ifndef GREETING_H
#define GREETING_H
#include <stdio.h>
#define MESSAGE "Hello, world!"
void print_message(void);
#endif
```
仅包含一个外部函数的声明和一个常量的定义。然后创建greeting.c自定义函数文件,随后便可在此文件中定义print_message函数的代码:
```
// greeting.c
#include "greeting.h"
void print_message(void) {
printf("%s\n", MESSAGE);
}
```
已经定义了在greeting.h中声明的print_message的函数的代码。最后,创建myapp.c主文件,请注意,此文件应包含main函数。main函数用于实现程序的执行流程,并调用位于greeting.h中声明的外部函数。下面是主文件的代码:
```
// myapp.c
#include "greeting.h"
int main(void) {
print_message();
return 0;
}
```
在主函数中调用print_message函数,并返回0作为程序的结束标志。现在,程序已完成编写,但需要一个makefile文件来告诉编译器构建程序的模块之间的依赖关系。
makefile文件定义了在构建工程时所需的规则和指令。在此示例中,makefile文件将使用三个变量来指定其构建模块的文件名。维护此变量的好处在于当文件名更改时,只需更新makefile文件,而不必更新每个文件内包含的文件名。
```
# makefile
# 定义三个变量
TARGET = myapp
DEPENDENCIES = greeting.o
SOURCE = myapp.c
# make 的规则
$(TARGET): $(DEPENDENCIES) $(SOURCE)
gcc -o $@ $^
greeting.o: greeting.c greeting.h
gcc -c $<
clean:
rm -f $(TARGET) $(DEPENDENCIES)
```
此文件包含一个“make”的规则和一个“clean”的规则。使greeting.o是$(TARGET)的依赖项,而除$(TARGET)外的所有文件都是$(TARGET)的依赖项。$(TARGET)的依赖项必须通过编译生成外部目标文件。最后,可使用以下命令来编译和运行程序:
```
$ make
$ ./myapp
Hello, world!
$ make clean
```
阅读全文