The static keyword in C is a storage-class specifier. It has different meanings, depending on the context. Inside a function it makes the variable to retain its value between multiple function calls. Outside of a function it restrains the visibility of the function or variable to the current file (compilation unit).
The syntax of the static keyword in C is very simple. When defining a variable or function, write the static modifier before the type or name.
These two are equivalent:
static <variable type> <variable name> <variable type> static <variable name>
And these are equivalent, too:
static <function type> <function name>() <function type> static <function name>()
Here are two examples of static variables:
int static callCount = 0; static int callCount = 0;
Here are two examples of static functions:
static void count() { ... } void static count() { ... }
In C, inside a function, we use the static modifier to declare variables with static storage duration. Such variables retain their value throughout multiple calls of the function. These variables are initialized only once at compile time. Their life time matches the life time of our program.
Look at the example below. The initialization statement callCount = 0 will not be executed a second time. The variable callCount will be initialized to 0 and it will be incremented with each call to the function count().
int main() { count(); count(); count(); } void count() { static int callCount = 0; ++callCount; printf("The function \"count\" was called %d times.\n", callCount); }
The output is:
The function
count was called 1 times.
The
function count was called 2 times.
The
function count was called 3 times.
The static keyword can be used with global variables and functions. In this context it limits their visibility to the current file (translation unit is more precise here). This means that we cannot access a static function or variable from another source file.
It is a good practice to declare most of your functions static. Leave visible only the functions that need to be accessed from other files. This principle is called encapsulation. If you come from an OOP language like Java or C#, this is similar to using private and public modifiers.
The same way we can hide the definition of a variable. This is useful when we want to define different variables with the same name in our source files.
The following definitions will give an error during compilation:
source1.c:
int count = 0;
source2.c:
int count = 0;
This will not compile and the error looks something like this:
(.bss+0x0): multiple definition of `count'
…or like this:
source2.obj : error LNK2005: _count already defined in source1.obj
To define different variables with the same
name on global level, you need to use the static keyword for at least one of
them:
source1.c:
static int count = 0;
source2.c:
static int count = 0;
static void count() { static int callCount = 0; ++callCount; printf("The function \"count\" was called %d times.\n", callCount); }
This is another use of the static keyword in C, although it is rarer. Since C99, we can tell the compiler a minimum number of elements that the array contains. This is only valid when we pass an array pointer to a function. Here is an example of usage:
void printArray(int myArray[static 10], int size) { int i; printf("["); for(i = 0; i < size; ++i) { printf("%d ", myArray[i]); } printf("]\n"); }
Sometimes this technique is used to guarantee that the argument will be not null.
void myFunction(int myArray[static 1], int size) { ... }
The following zip file contains the source files for all of the examples above. As always you can download it for free: static-keyword-in-c.zip
In C, the static variables are placed in the BSS or DATA segments. The BSS segment contains the uninitialized data. The DATA segment keeps the initialized data.
Related reading: other storage class specifiers: