92

I have two source files that need to access a common variable. What is the best way to do this? e.g.:

source1.cpp:

int global;

int function();

int main()
{
    global=42;
    function();
    return 0;
}

source2.cpp:

int function()
{
    if(global==42)
        return 42;
    return 0;
}

Should the declaration of the variable global be static, extern, or should it be in a header file included by both files, etc?

kaykun
  • 2,247
  • 2
  • 24
  • 37
  • Possible duplicate of [this question](http://stackoverflow.com/questions/3591772/). – fredoverflow Sep 02 '10 at 14:14
  • 8
    Rework the code to use something other than global variables - or retag the question as "C". When I need a global in C++, I typically make it a static member of a class that is publicly readable via an accessor method. If the scope can be narrowed down so that only internal class members use the accessor, all the better. Few variables are truly "global". – Steve Townsend Sep 02 '10 at 14:14
  • 1
    depends on what you want to do – Chubsdad Sep 02 '10 at 14:24
  • `function()` is also common to both sources and needs the same treatment. With respect to `global` the "best way" is *not* to do that at all. http://www.eetimes.com/discussion/break-point/4025723/A-pox-on-globals – Clifford Sep 02 '10 at 14:30
  • How is a static class member not “truly global”? That sounds like achieving the same thing differently just for the sake of “being C++”. – Maëlan Sep 15 '21 at 11:44

4 Answers4

158

The global variable should be declared extern in a header file included by both source files, and then defined in only one of those source files:

common.h

extern int global;

source1.cpp

#include "common.h"

int global;

int function(); 

int main()
{
    global=42;
    function();
    return 0;
}

source2.cpp

#include "common.h"

int function()
{
    if(global==42)
        return 42;
    return 0;
}
e.James
  • 116,942
  • 41
  • 177
  • 214
20

You add a "header file", that describes the interface to module source1.cpp:

source1.h

#ifndef SOURCE1_H_
#define SOURCE1_H_

extern int global;

#endif

source2.h

#ifndef SOURCE2_H_
#define SOURCE2_H_

int function();

#endif

and add an #include statement in each file, that uses this variable, and (important) that defines the variable.

source1.cpp

#include "source1.h"
#include "source2.h"

int global;     

int main()     
{     
    global=42;     
    function();     
    return 0;     
}

source2.cpp

#include "source1.h"
#include "source2.h"

int function()            
{            
    if(global==42)            
        return 42;            
    return 0;            
}

While it is not necessary, I suggest the name source1.h for the file to show that it describes the public interface to the module source1.cpp. In the same way source2.h describes what is public available in source2.cpp.

harper
  • 13,345
  • 8
  • 56
  • 105
2

In one file you declare it as in source1.cpp, in the second you declare it as

extern int global;

Of course you really don't want to be doing this and should probably post a question about what you are trying to achieve so people here can give you other ways of achieving it.

Patrick
  • 8,175
  • 7
  • 56
  • 72
  • 1
    You should achieve that the compiler gets the same extern declaration for each compilation unit, that needs the declaration. When you spread the externs over all files that needs extern access to the variable, function, ... it is difficult to keep them in sync. That's why: don't declare extern in the consuming .cpp file. – harper Sep 02 '10 at 14:29
0

You don't want to use global variable, but there are cases where you don't have a choice. If you work with a tranceiver that use multiple communication protcols, UART, I2C, SPI the tranceiver will have a handle and if you implement mutiple drivers files using the tranceiver functions you will have to share the tranceiver handle between all the drivers. There is no way around a global variable if you like to keep your architecture logical: Apllication Layer, Driver Layer, HAL Layer and Low level Layer.

Marco
  • 2,368
  • 6
  • 22
  • 48
Yacine
  • 1