我有以下文件:
我需要使用 3 个全局变量:freq、amp 和 waveforms。
我是否应该使用 extern 在每个 .h 文件中声明这些变量并在其中一个 .c 文件中定义变量或创建一个 global_variable.h,在 global_variable.h 中声明这些变量并在每个 .c 中包含此 global_variable.h文件。
这是最小的可复制示例:
变化频率.c
#include "change_freq.h"
void increment_freq(double *frequency)
{
(*frequency)++;
if (*frequency == 1)
{
amp++;
}
}
change_freq.h
#ifndef CHANGE_FREQ_H
#define CHANGE_FREQ_H
#include "global_variables.h"
void increment_freq(double *frequency);
#endif
global_variables.h
#ifndef GLOBAL_VARIABLES_H
#define GLOBAL_VARIABLES_H
double freq;
double amp;
#endif
main.c
#include "global_variables.h"
#include "change_freq.h"
int main()
{
freq = 0;
increment_freq(&freq);
printf("Hello World!\n");
printf("freq %lf\n", freq);
printf("amp %lf\n", amp);
return 0;
}
你的代码看起来几乎没问题。
这是你应该做的:
change_freq.c
#include "change_freq.h"
#include "global_variables.h" // <<< add this line
void increment_freq(double frequency)
{
frequency++;
if (frequency == 1)
{
amp++;
}
}
change_freq.h
#ifndef CHANGE_FREQ_H
#define CHANGE_FREQ_H
// #include "global_variables.h" <<< remove this line
void increment_freq(double frequency);
#endif
global_variables.h
#ifndef GLOBAL_VARIABLES_H
#define GLOBAL_VARIABLES_H
extern double freq; // << put extern here
extern double amp;
#endif
main.c
#include <stdio.h>
#include "global_variables.h"
#include "change_freq.h"
double freq; // << define your global variables here
double amp;
int main()
{
...
我需要使用的 3 个全局变量:
、freq
和amp
.waveforms
每个全局变量的声明应该只出现在一个
.h
文件中。
用于这些声明的
.h
文件应该与变量相关。鉴于 OP 关于变量的详细信息不足,建议使用新的 .h 文件。
.c 文件应在需要时包含 .h。
我应该在每个 .h 文件中声明这些变量
不,只是在一个`.h文件中。
OP的代码有问题:
// global_variables.h
#ifndef GLOBAL_VARIABLES_H
#define GLOBAL_VARIABLES_H
double freq; // The is not only a declaration, but also a definition.
double amp;
#endif
使用
extern
:
// global_variables.h
#ifndef GLOBAL_VARIABLES_H
#define GLOBAL_VARIABLES_H
extern double freq; // The is only a declaration.
extern double amp;
#endif
我应该...创建一个 global_variable.h,在 global_variable.h 中声明这些变量,并将这个 global_variable.h 包含在每个 .c 文件中。
没有。在 1 个或多个 .h 文件中声明全局变量。 (1 可能足以完成此任务)在 .c 文件中包含 need 的 .h 文件。
包括不需要的
在OP的示例代码中:
#include "global_variables.h"
不需要。
#ifndef CHANGE_FREQ_H
#define CHANGE_FREQ_H
// #include "global_variables.h"
void increment_freq(double frequency);
#endif
无法复制 OP 的“对 `increment_freq' 的未定义引用”。
这是一个重现项目设置的脚本(在空目录中运行):
#!/bin/sh -eu
cat > global_variables.h <<EOF
#ifndef GLOBAL_VARIABLES_H
#define GLOBAL_VARIABLES_H
double freq;
double amp;
#endif
EOF
cat > change_freq.h <<EOF
#ifndef CHANGE_FREQ_H
#define CHANGE_FREQ_H
#include "global_variables.h"
void increment_freq(double *frequency);
#endif
EOF
cat > change_freq.c <<EOF
#include "change_freq.h"
void increment_freq(double *frequency)
{
(*frequency)++;
if (*frequency == 1)
{
amp++;
}
}
EOF
cat > main.c <<EOF
#include "global_variables.h"
#include "change_freq.h"
#include <stdio.h> ///ADD!
int main()
{
freq = 0;
increment_freq(&freq);
printf("Hello World!\n");
printf("freq %lf\n", freq);
printf("amp %lf\n", amp);
return 0;
}
EOF
这样就可以编译运行了(
cc *.c && ./a.out
)
如果仅当您的编译器和链接器支持所谓的common variables,它允许未初始化的全局变量(double freq; double amp;
)在多个翻译单元中暂时定义,然后链接器将它们合并。对于 gcc/clang,您可以使用 -fcommon
. 明确请求此非标准功能
便携式解决方案是做
extern double freq,amp;
在标题中 和
/*no-extern*/ double freq,amp;
在其中一个 C 文件中。
( 你看到
double freq;
double amp;
在全局范围内没有 extern
和初始值设定项都是声明和暂定定义。
暂定定义意味着你可以用初始化器重新定义它们,之后它们就完成了,或者重新暂定定义它们。如果没有给出初始化器,它们默认为零初始化,并在编译单元结束时完成。 (相当常见的)-fcommon
扩展(也需要链接器的支持)允许您将暂定全局的概念扩展到多个翻译单元。如果我没记错的话,这是 B 的遗留功能。)