In the first example, main2.cpp defines the global variable i , which could be accessed by main.cpp if the extern i declaration appeared in this file. (Usually, the extern declaration comes from the header file.) You have encountered a compiler error since i never declared in main.cpp , which means that the compiler assumes that there is no such variable.
In your second example, main2.cpp defines the scope variable of the i file. File scope variables are different from global, even if they have the same name. If in the second example you had an extern i declaration in main.cpp , both files would be compiled successfully, but then you would get a link error because the global variable i was not defined.
If you renamed main2.cpp from the second example to main3.cpp , added the extern declaration from i to main.cpp , compiled all three and linked everything together, which would be successful; main.cpp and main2.cpp will use the same variable named i , and main3.cpp will have its own completely separate variable, also called i .
This material is called bond. Namespaces are almost completely unrelated to binding. However, an anonymous namespace is special. Defining a variable in an anonymous namespace for all practical purposes is the same as defining it with static β making it a variable in the file area. (If I remember correctly, there is a difference, but it only matters if you do complex things with exported templates, and since the exported templates are used so little that they say about removing a function from the C ++ standard, I have to worry about it.)
The value of the anonymous namespace is that you can put a class definition in it, and that makes all the class methods local. (To get this effect, there should only be a class { ... } block inside the namespace { ... } block.) You cannot do this in any other way.
source share