94

See subject. What were they thinking?

UPDATE: Changed from "static" to "internal linkage" to save confusion.

To give an example... Putting the following in a file:

const int var_a = 1;
int var_b = 1;

...and compiling with g++ -c test.cpp only exports var_b.

Johan Kotlinski
  • 25,185
  • 9
  • 78
  • 101

7 Answers7

126

I believe you mean

Why does const imply internal linkage in C++

It's true that if you declare a const object at namespace scope, then it has internal linkage.

Appendix C (C++11, C.1.2) gives the rationale

Change: A name of file scope that is explicitly declared const, and not explicitly declared extern, has internal linkage, while in C it would have external linkage

Rationale: Because const objects can be used as compile-time values in C++, this feature urges programmers to provide explicit initializer values for each const. This feature allows the user to put const objects in header files that are included in many compilation units.

Community
  • 1
  • 1
Johannes Schaub - litb
  • 496,577
  • 130
  • 894
  • 1,212
  • 2
    It seems non-const global objects can also be initialized, but why standard doesn't give it internal linkage? – Yong Li Sep 15 '17 at 07:54
17

As litb said, const objects have internal linkage in C++. This is because they are intended to be used like this:

// a.cpp
const int BUFSIZE = 100;
char abuf[BUFSIZE];

// b.cpp
const int BUFSIZE = 256
int bbuf[BUFSIZE];
7

Const and static are orthogonal concepts in both C and C++.

The const keyword tells the compiler to disallow the variable from appearing as the lvalue of any expression - essentially making it read-only.

In C, the static keyword has several uses depending on what it is applied to. When applied to a variable of a function, it indicates that the variable is not stored in the local scope of a function, but is accessible across invocations of it. When applied to a global variable or function, it becomes accessible only to a particular file - in other words, it is accessible only within the compilation unit (unless declared extern).

In C++, the static keyword can be used within a class definition, to make a variable or functions shared across all instances of the class, rather than being local to each instance. Furthermore, a static class function in C++ can only access static variables of that class (or classes it has access to). Now, in C++ const does give members internal linkage to the compilation unit unless they are explicitly declared extern - this may be what you are referring it. This allows compile-time constants to be shared across unit through the use of header files. Keep in mind, though, that the members are not really static - rather the constant is compiled into each location where it is referenced.

LBushkin
  • 129,300
  • 32
  • 216
  • 265
6

In C & C++ the term static has multiple meanings (it can govern linkage and storage) You'll have to read Stroustrup's D&E to appreciate his rationale - but when you declare a variable to be const at namespace scope it automatically has internal linkage - whereas in C you have to declare it static to force it to have internal linkage.

Of course in C++, the use of static to control linkage has been deprecated, anonymous namespaces can be used to simulate internal linkage in C++.

const variables in C++ were supposed to replace preprocessor constants - and since preprocessor constants are only visible in files that define them, similarly, const automatically makes the variable visible only in the file that defines it.

Martin Cote
  • 28,864
  • 15
  • 75
  • 99
Faisal Vali
  • 32,723
  • 8
  • 42
  • 45
4

Those concepts are orthogonal and should not be thought as the same thing.

Constness is an access propriety : it tells only if your variable should be read-only (const) or write-read (non-const).

Staticity is a life-time (and technically memory localization) property : it tells if the variable will be global in the scope of a class (when in a class) or a translation unit (when used with a global variable defined in a cpp).

Klaim
  • 67,274
  • 36
  • 133
  • 188
-2

It doesn't, and the most obvious example is that if you have a const member variable (which is initialised by the constructor, of course), it is not shared by all objects of that class, but individual to each.

class A {
public:
  A(int newx) : x(newx);
private
  int x;
}

litb gives the best answer, above.

Alex Brown
  • 41,819
  • 10
  • 94
  • 108
-7

It doesn't. Writing the following:

const int i = 0;

doesn't make i static (in either C or C++).

Martin Cote
  • 28,864
  • 15
  • 75
  • 99