A scope is a namespace for user-defined types, typedef-ed types, constants and native functions.
There is always a global scope, a scope that represents the source file itself. All enumerations, typedefs and user-defined types declared in the file (and not enclosed by other user-defined types) are said to be defined at the global scope.
// beginning of the file
typedef int MyIntType;
enum MyEnum
{
// …
};
const MyConstant = 5;
struct MyStruct
{
// …
};
In the example above, all identifiers, that is, MyIntType
, MyEnum
, MyConstant
and MyStruct
are declared in the global scope.
Each user-defined type creates its own scope:
struct A // A is declared in the global scope and creates its own scope
{
const B = 10; // B is declared in scope of structure A
};
Every enclosed scope “sees” all its parent scopes. That is, when name-lookup is performed (for the search of the identifier), first, the most enclosed scope is searched. If the identifier is not found, a parent scope is searched and so on.
This allows an identifier to be overloaded in the enclosed scope:
const MyConstant = 10;
struct A
{
const MyConstant = 5;
int array[MyConstant]; // will use MyConstant from the A scope
};
struct B
{
int array[MyConstant]; // will use MyConstant from the global scope
};
A compiler does not provide a way to reference MyConstant
from the global scope from scope A in this example. But once the scope is closed, a global scope is active again (see structure B).
Enumerations are slightly different in a way they use scopes: enumeration declaration does not create a scope but places all enumeration values into the parent scope. See the enumerations section for more information.