Static in C++
Static variables/functions, static in the context of class/struct
Internal linkage and external linkage
When you write an implementation file (.cpp, .cxx, etc) your compiler generates a translation unit. This is the source file from your implementation plus all the headers you #included in it.
Internal linkage
refers to everything only in scope of a translation unit.
External linkage
refers to things that exist beyond a particular translation unit. In other words, accessible through the whole program, which is the combination of all translation units (or object files).
Internal linkage can be achieved by using static
keyword. Let’s see an example where we have two .cpp files.
main.cpp
1 |
|
static.cpp
1 | int a = 5; |
compile and run:
1 | g++ main.cpp static.cpp -o main |
int a = 5;
is extern by default. Other translation unit (main.cpp) has access to it. If we change static.cpp to:
static.cpp
1 | static int a = 5; |
The compiler will give us errors as following. This is because a
is now only visible in the scope of its translation unit. Other translation units are not accessible.
1 | main.cpp:(.text+0xa): undefined reference to `a' |
const
variables are also static by default and only accessible in the scope of a translation unit. However, we can explicitly declare them as extern
to be able to extend to other files.
main.cpp
1 |
|
static.cpp
1 | static int a = 5; |
compile and run:
1 | 8 |
We are using ci
declared in static.cpp.
Static in a function
When a variable is declared as static, memory will be allocated for the lifetime of the program. Even if the function gets called multiple times, the space for the static variable will only be allocated once and the its value will get carried through the next call.
1 | void foo() { |
output:
1 | 0 |
Static in class
When we declare a member of class as static, only one copy of the static member is maintained no matter how many objects of the class we create. Thus, a static member is shared by all the objects. It can be initialized outside of the class using scope resolution operator ::
. Static members can not be initialized using constructors.
1 | class Base { |
1 | number of objects: 2 |
Just like static variables, static member functions also do not depend on the object of the class. We can use the class name followed by ::
to invoke the static member functions. Note that
static member functions can only access the static member variable and functions. They can not access non-static data of the class.
1 | class Base { |
1 | Line 12: Char 22: error: invalid use of member 'm_a' in static member function |
We change m_a
to m_count
in foo()
1 | class Base { |
1 | 2 |
References
Static in C++