Multiple definition and header-only libraries
If you define your variables inside your header file and include the header in several c files, you are bound to get multiple definitions error because you break the One definition rule(ODR), which states that there should be only one definition in one Translation Unit(header files + source file).
Solution is:
You should define the entities you get Multiple definition errors for only once.
For Functions:
Declare the function prototypes in header file(which you include in other source files) and define the function in one and only one source file.
For Global variables:
You declare the variable extern in header file(which you include in other source files) and then define the variable in one and only one source file.
One header file in multipe cpp files: Multiple definition
There are 2 solutions to this problem.
Solution 1
You can add the keyword inline
infront of the function like:
myfile.h
#ifndef UTILS
#define UTILS
inline void toUpper(string &str) {
for(unsigned int i=0; i<str.length(); i++) {
str.at(i) = toupper(str.at(i));
}
}
inline void toLower(string &str) {
for(unsigned int i=0; i<str.length(); i++) {
str.at(i) = tolower(str.at(i));
}
}
#endif // UTILS
Now you can include this header in different files without getting the mentioned error.
Solution 2
You can create a separate .cpp file and put the definition there. This would look like:
myfile.h
#ifndef UTILS
#define UTILS
//just declarations here
void toUpper(string &str); //note no inline keyword needed here
void toLower(string &str); //note no inline keyword needed here
#endif // UTILS
myfile.cpp
#include "myheader.h"
void toUpper(string &str) {
for(unsigned int i=0; i<str.length(); i++) {
str.at(i) = toupper(str.at(i));
}
}
void toLower(string &str) {
for(unsigned int i=0; i<str.length(); i++) {
str.at(i) = tolower(str.at(i));
}
}
Multiple definition error using header file
Your header file file2048.h
contains variable declarations. When you include this file in other sorces files this causes the variable to be declader multiple times. Please look into the extern
keyword.
Header File:
#ifndef FILE2048_H
#define FILE2048_H
#define SIZE 4
#ifdef __cplusplus
extern "C" {
#endif
/* - Bad implementation
int matrix[SIZE+1][SIZE+1]={0};
*/
//Better implementation
extern int matrix[SIZE+1][SIZE+1];
//Now define this variable only once, on "main.c" for example
.
.
.
#endif
Why does defining functions in header files create multiple definition errors, but not classes?
Generally when you compile a definition that is namespace scoped (like functions or global variables), your compiler will emit a global symbol for it. If this appears in multiple translation units, there will be a conflict during link-time since there are multiple definitions (which happen to be equivalent, but the linker can't check this).
This is part of the one definition rule: Exactly one definition of a function or variable is allowed in the entire program, in one of the translation units.
There are some exceptions to this, for example, class definitions and inline functions/variables. However, definitions must be the exact same (textually) in all the translation units they appear in. Class definitions are meant to be #include
d, so it makes sense to allow them to appear in multiple translation units.
If you define a member function inside the class body they are implicitly inline
because otherwise you would not be able to include the class definition with the member function definition without breaking ODR. For example, these three are functionally equivalent:
struct TestStruct {
int x;
int test() { return 10; }
};
// Could have been written
struct TestStruct {
int x;
inline int test() { return 10; }
};
// Or as
struct TestStruct {
int x;
int test(); // The `inline` specifier could also be here
};
inline int TestStruct::test() { return 10; }
You can do this to your namespace scoped functions/variables too: inline int test() { return 5; }
and inline int x = 20;
would have compiled with no further issue.
This is implemented by the compiler emitting "specially marked" symbols for inline entities, and the linker picking one arbitrarily since they should all be the same.
The same exception to ODR also exists for templated functions / variables and enum declarations, since they are also meant to live in header files.
Multiple definition error on variable that is declared and defined in header file and used only in its cpp file
If you declare your variable in the header file:
#ifndef GLOBAL_H
#define GLOBAL_H
int foo = 0;
#endif
In every include of your header file or translation unit, a new instance of your integer is created. As you mentioned, to avoid this, you need to declare the item as "extern" in the header file and initialize it in the implementation file:
// .h
extern int foo;
// .cpp
int foo = 0
A more C++ way to do that can be something like this:
#ifndef GLOBAL_H
#define GLOBAL_H
struct Global {
static int foo;
};
#endif
And in your cpp file:
#include "variables.h"
int Global::foo = 0;
C++17 fixes this problem with inline variables, so you can do:
#ifndef GLOBAL_H
#define GLOBAL_H
inline int foo = 0;
#endif
See How do inline variables work? for more information.
multiple definition in header file
The problem is that the following piece of code is a definition, not a declaration:
std::ostream& operator<<(std::ostream& o, const Complex& Cplx) {
return o << Cplx.m_Real << " i" << Cplx.m_Imaginary;
}
You can either mark the function above and make it "inline" so that multiple translation units may define it:
inline std::ostream& operator<<(std::ostream& o, const Complex& Cplx) {
return o << Cplx.m_Real << " i" << Cplx.m_Imaginary;
}
Or you can simply move the original definition of the function to the "complex.cpp" source file.
The compiler does not complain about "real()" because it is implicitly inlined (any member function whose body is given in the class declaration is interpreted as if it had been declared "inline"). The preprocessor guards prevent your header from being included more than once from a single translation unit ("*.cpp" source file"). However, both translation units see the same header file. Basically, the compiler compiles "main.cpp" to "main.o" (including any definitions given in the headers included by "main.cpp"), and the compiler separately compiles "complex.cpp" to "complex.o" (including any definitions given in the headers included by "complex.cpp"). Then the linker merges "main.o" and "complex.o" into a single binary file; it is at this point that the linker finds two definitions for a function of the same name. It is also at this point that the linker attempts to resolve external references (e.g. "main.o" refers to "Complex::Complex" but does not have a definition for that function... the linker locates the definition from "complex.o", and resolves that reference).
Avoid multiple definitions of headers
Put the definitions into the cpp file. If you put them to the header, they will be defined in every cpp file which includes the header.
GameObject.h
#ifndef GAMEOBJECT_H
#define GAMEOBJECT_H
extern float cube[];
...
typedef struct GameObject
{
int ID, parent;
Vector3 position;
Quaternion rotation;
};
extern GameObject GameObjects[65536];
...
#endif
GameObject.cpp
#include "GameObject.h"
float cube[] = {...};
...
GameObject GameObjects[65536];
multiple definition error c++
Since I could not find any complete (in my view) duplicate for this question, I am going to write a (hopefully) authoritive and complete answer.
What is One Definition Rule and why should I care
A One Definition Rule, usually dubbed ODR, is a rule which states (simplified) that any entity (informal term) used in the program should be defined once, and only once. An entity which is defined more than once is often causing a compilation or linker error, but sometimes can be left undetected by the compiler and lead to very hard-to-trace bugs.
I am not going to formally define entity here, but one can think of it as a function, variable or class. Before going further, one should very clear understand the difference between definition and declaration in C++, since while double definition is prohibited, double declaration is usually unavoidable.
Definition vs. declaration
Every entity used in the code should be declared in the given translation unit (translation unit is usually a cpp source file together with all header files included in it, directly or indirectly through other header files). The way an entitty is declared differes based on the entity itself. See below on how to declare different types of entities. Entities are often declared in header files. Since most complex application has more than one translation unit in it (more than one cpp file), and different cpp files often include the same headers, an application is likely to have multiple declarations for many entities used. Like I said above, this is not a problem.
Every entity used in the application, must be defined once and only once. The term 'application' is used a bit loosely here - for example, libraries (both static and dynamic) can have entities (at this point usually called symbols) left undefined within them, and an executable which was linked to use a dynamic library can have a symbol undefined as well. Instead, I refer to the application is an ultimate running something, after all the libraries have been statically or dynamically linked into it, and symbols resolved.
It is also worth noting that every definition serves as a declaration as well, meaning, that whenever you define something, you are also declaring the same thing.
As with declaration, the way to define an entity differes by the type of entity. Here is how one can declare/define 3 basic types of entities - variables, classes and functions - based on it's type.
Variables
Variables are declared using following construct:
extern int x;
This declares a variable x. It does not define it! A following piece of code will be compiled OK, but an attempt to link it without any other input files (for example, with g++ main.cpp
) will produce a link-time error due to undefined symbols:
extern int x;
int main() {
return x;
}
The following piece of code defines variable x:
int x;
If this single line were to be put into file x.cpp, and this file compiled/linked together with main.cpp from above with g++ x.cpp main.cpp -o test
it would compile and link without problems. You could even run resulting executable, and if you are to check exit code after the executable was run, you'd notice it is 0. (Since global variable x would be default-initialized to 0).
Functions
Functions are declared by providing their prototypes. A typical function declaration looks like following:
double foo(int x, double y);
This construct declares a function foo
, returning double
and accepting two arguments - one of type int
, another of type double
. This declaration can appear multiple times.
Following code defines above mentioned foo
:
void foo(int x, double y) {
return x * y;
}
This definition can only appear once in the whole application.
Function definition has an additional quirk to variable definition. If above definition of foo
were to put into header file foo.h
, which in turn would be included by two cpp files 1.cpp
and 2.cpp
, which are compiled/linked together with g++ 1.cpp 2.cpp -o test
you would have a linker error, saying that foo()
is defined twice. This might be prevented by using following form of foo
declaration:
inline void foo(int x, double y) {
return x * y;
}
Note inline
there. What it tells compiler is that foo
can be included by multiple .cpp files, and this inclusion should not produce linker error. Compiler have several options on how to make this happen, but it can be relied upon to do it's job. Note, it would still be an error to have this definition twice in the same translation unit! For example, following code will produce a compiler error
inline void foo() { }
inline void foo() { }
It is worth noting, that any class method defined within the class is implictly inline, for example:
class A {
public:
int foo() { return 42; }
};
Here A::foo() is defined inline
.
Classess
Classess are declared by following construct:
class X;
Above declaration declares class X (and at this point X is formally called an incomplete type), so that it can be used when information about it contents, such as it's size or it's members is not needed. For example:
X* p; // OK - no information about class X is actually required to define a pointer to it
p->y = 42; // Error - compiler has no idea if X has any member named `y`
void foo(X x); // OK - compiler does not need to generated any code for this
void foo(X x) { } // Error - compiler needs to know the size of X to generate code for foo to properly read it's argument
void bar(X* x) { } // OK - compiler needs not to know specifics of X for this
A definition of class is well-known to everybody, and follows this construct:
class X {
public:
int y;
};
This makes a class X defined, and now it can be used in any context. An important note - class definition has to be unique per tralnlation unit, but does not have to be unique per application. That is, you can have X defined only once per translation unit, but it can be used in multiple files linked together.
How to properly follow ODR rules
Whenever a same entity is defined more than once in the resulting application, so-called ODR violation happenes. Most of the time, a linker will see the violation and will complain. However, there are cases when ODR violation does not break linking and instead causes bugs. This might happen, for example, when the same .cpp file defining a global variable X is put into both application and dynamic library, which is loaded on demand (with dlopen
). (Yours trully spent a couple of days trying to trace a bug happened because of that.)
A more conventional causes of ODR violations are:
Same entity defined twice in the same file in the same scope
int x;
int x; // ODR violation
void foo() {
int x;
} // No ODR violation, foo::x is different from x in the global scope
Prevention: don't do this.
Same entity defined twice, when it was supposed to be declared
(in x.h)
int x;
(in 1.cpp)
#include <x.h>
void set_x(int y) {
x = y;
}
(in 2.cpp)
#include <x.h>
int get_x() {
return x;
}
While the wisdom of above code is questionable at best, in serves a point of illustrating ODR rule. In the code above, variable x is supposed to be shared between two files, 1.cpp and 2.cpp, but was coded incorrectly. Instead, the code should be following:
(in x.h)
extern int x; //declare x
(in x.xpp)
int x; // define x
// 1.cpp and 2.cpp remain the same
Prevention
Know what you are doing. Declare entities when you want them declared, do not define them.
If in the example above we'd use function instead of the variable, like following:
(in x.h)
int x_func() { return 42; }
We would have a problem which could be solved in two ways (as mentioned above). We could use inline
function, or we could move definition to the cpp file:
(in x.h)
int x_func();
(in x.cpp)
int x_func() { return 42; }
Same header file included twice, causing the same class defined twice
This is a funny one. Imagine, you have a following code:
(in a.h)
class A { };
(in main.cpp)
#include <a.h>
#include <a.h> // compilation error!
The above code is seldom appearing as written, but it is quite easy to have the same file included twice through the intermediate:
(in foo.h)
#include <a.h>
(in main.cpp)
#include <a.h>
#include <foo.h>
Prevention Traditional solution to this is to use so-called include guards, that is, a special preprocessor definitions which would prevent the double-inclusion. In this regard, a.h should be redone as following:
(in a.h)
#ifndef INCLUDED_A_H
#define INCLUDED_A_H
class A { };
#endif
The code above will prevent inclusion of a.h into the same translation unit more than once, since INCLUDED_A_H
will become defined after first inclusion, and will fail #ifndef
on all subsequent ones.
Some compilers expose other ways to control inclusion, but to date include guards remain the way to do it uniformely across different compilers.
Multiple definitions of same function in C++
You must write code of random_double()
in .cpp file other than .hpp or .h file. Or, add inline
before double random_double() { //some code }
if you keep your code in your .hpp file.
Related Topics
Call a C Function from C++ Code
Determine the Size of a C++ Array Programmatically
Confused When Boost::Asio::Io_Service Run Method Blocks/Unblocks
How to Call a Function on All Variadic Template Args
Magic Number in Boost::Hash_Combine
How to Get Console Output in C++ With a Windows Program
A Free Tool to Check C/C++ Source Code Against a Set of Coding Standards
Creating All Possible K Combinations of N Items in C++
Representing 128-Bit Numbers in C++
Static Constructors in C++? I Need to Initialize Private Static Objects
How to Printf Uint64_T? Fails With: "Spurious Trailing '%' in Format"
How to Use a Member Variable as a Default Argument in C++
What Does a Colon Following a C++ Constructor Name Do
How to Do an Integer Log2() in C++