For some reason, I'm getting multiple declarations of content within my header file even though I'm using header guards. My example code is below:
main.c:
#include "thing.h"
int main(){
printf("%d", increment());
return 0;
}
thing.c:
#include "thing.h"
int increment(){
return something++;
}
thing.h:
#ifndef THING_H_
#define THING_H_
#include <stdio.h>
int something = 0;
int increment();
#endif
When I attempt to compile this, GCC says that I have multiple definitions of the something variable. ifndef should make sure that this doesn't happen, so I'm confused why it is.
Header guards are designed to ensure that the contents of a given header file are not copied more than once into any single file, in order to prevent duplicate definitions.
In the C and C++ programming languages, an #include guard, sometimes called a macro guard, header guard or file guard, is a particular construct used to avoid the problem of double inclusion when dealing with the include directive.
Header Guards in C++ are conditional compilation directives that help to avoid errors that arise when the same function or variable is defined more than once by the mistake of a programmer. According to C++, when a function or a variable is defined more than once, it yields an error.
The include guards are functioning correctly and are not the source of the problem.
What happens is that every compilation unit that includes thing.h
gets its own int something = 0
, so the linker complains about multiple definitions.
Here is how you fix this:
thing.c:
#include "thing.h"
int something = 0;
int increment(){
return something++;
}
thing.h:
#ifndef THING_H_
#define THING_H_
#include <stdio.h>
extern int something;
int increment();
#endif
This way, only thing.c
will have an instance of something
, and main.c
will refer to it.
You have one definition in each translation unit (one in main.c
, and one in thing.c
). The header guards stop the header from being included more than once in a single translation unit.
You need to declare something
in the header file, and only define it in thing.c
, just like the function:
thing.c:
#include "thing.h"
int something = 0;
int increment(void)
{
return something++;
}
thing.h:
#ifndef THING_H_
#define THING_H_
#include <stdio.h>
extern int something;
int increment(void);
#endif
The header guards will stop the file from being compiled more than once in the same compilation unit (file). You are including it in main.c and thing.c, so it will be compiled once in each, leading to the variable something
being declared once in each unit, or twice in total.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With