This commit is contained in:
2025-10-25 03:02:53 +03:00
commit 043225d523
3416 changed files with 681196 additions and 0 deletions

150
cppdraft/namespace/def.md Normal file
View File

@@ -0,0 +1,150 @@
[namespace.def]
# 9 Declarations [[dcl]](./#dcl)
## 9.9 Namespaces [[basic.namespace]](basic.namespace#namespace.def)
### 9.9.2 Namespace definition [namespace.def]
#### [9.9.2.1](#general) General [[namespace.def.general]](namespace.def.general)
[namespace-name:](#nt:namespace-name "9.9.2.1General[namespace.def.general]")
[*identifier*](lex.name#nt:identifier "5.11Identifiers[lex.name]")
[*namespace-alias*](namespace.alias#nt:namespace-alias "9.9.3Namespace alias[namespace.alias]")
[namespace-definition:](#nt:namespace-definition "9.9.2.1General[namespace.def.general]")
[*named-namespace-definition*](#nt:named-namespace-definition "9.9.2.1General[namespace.def.general]")
[*unnamed-namespace-definition*](#nt:unnamed-namespace-definition "9.9.2.1General[namespace.def.general]")
[*nested-namespace-definition*](#nt:nested-namespace-definition "9.9.2.1General[namespace.def.general]")
[named-namespace-definition:](#nt:named-namespace-definition "9.9.2.1General[namespace.def.general]")
inlineopt namespace [*attribute-specifier-seq*](dcl.attr.grammar#nt:attribute-specifier-seq "9.13.1Attribute syntax and semantics[dcl.attr.grammar]")opt [*identifier*](lex.name#nt:identifier "5.11Identifiers[lex.name]") { [*namespace-body*](#nt:namespace-body "9.9.2.1General[namespace.def.general]") }
[unnamed-namespace-definition:](#nt:unnamed-namespace-definition "9.9.2.1General[namespace.def.general]")
inlineopt namespace [*attribute-specifier-seq*](dcl.attr.grammar#nt:attribute-specifier-seq "9.13.1Attribute syntax and semantics[dcl.attr.grammar]")opt { [*namespace-body*](#nt:namespace-body "9.9.2.1General[namespace.def.general]") }
[nested-namespace-definition:](#nt:nested-namespace-definition "9.9.2.1General[namespace.def.general]")
namespace [*enclosing-namespace-specifier*](#nt:enclosing-namespace-specifier "9.9.2.1General[namespace.def.general]") :: inlineopt [*identifier*](lex.name#nt:identifier "5.11Identifiers[lex.name]") { [*namespace-body*](#nt:namespace-body "9.9.2.1General[namespace.def.general]") }
[enclosing-namespace-specifier:](#nt:enclosing-namespace-specifier "9.9.2.1General[namespace.def.general]")
[*identifier*](lex.name#nt:identifier "5.11Identifiers[lex.name]")
[*enclosing-namespace-specifier*](#nt:enclosing-namespace-specifier "9.9.2.1General[namespace.def.general]") :: inlineopt [*identifier*](lex.name#nt:identifier "5.11Identifiers[lex.name]")
[namespace-body:](#nt:namespace-body "9.9.2.1General[namespace.def.general]")
[*declaration-seq*](dcl.pre#nt:declaration-seq "9.1Preamble[dcl.pre]")opt
[1](#general-1)
[#](http://github.com/Eelis/draft/tree/9adde4bc1c62ec234483e63ea3b70a59724c745a/source/declarations.tex#L8270)
Every [*namespace-definition*](#nt:namespace-definition "9.9.2.1General[namespace.def.general]") shall inhabit a namespace scope ([[basic.scope.namespace]](basic.scope.namespace "6.4.6Namespace scope"))[.](#general-1.sentence-1)
[2](#general-2)
[#](http://github.com/Eelis/draft/tree/9adde4bc1c62ec234483e63ea3b70a59724c745a/source/declarations.tex#L8273)
In a [*named-namespace-definition*](#nt:named-namespace-definition "9.9.2.1General[namespace.def.general]") D,
the [*identifier*](lex.name#nt:identifier "5.11Identifiers[lex.name]") is the name of the namespace[.](#general-2.sentence-1)
The [*identifier*](lex.name#nt:identifier "5.11Identifiers[lex.name]") is looked up
by searching for it in the scopes of the namespace A in which D appears
and of every element of the inline namespace set of A[.](#general-2.sentence-2)
If the lookup finds a [*namespace-definition*](#nt:namespace-definition "9.9.2.1General[namespace.def.general]") for a namespace N,D [*extends*](#def:namespace,extend "9.9.2.1General[namespace.def.general]") N,
and the target scope of D is the scope to which N belongs[.](#general-2.sentence-3)
If the lookup finds nothing, the [*identifier*](lex.name#nt:identifier "5.11Identifiers[lex.name]") is introduced
as a [*namespace-name*](#nt:namespace-name "9.9.2.1General[namespace.def.general]") into A[.](#general-2.sentence-4)
[3](#general-3)
[#](http://github.com/Eelis/draft/tree/9adde4bc1c62ec234483e63ea3b70a59724c745a/source/declarations.tex#L8287)
Because a [*namespace-definition*](#nt:namespace-definition "9.9.2.1General[namespace.def.general]") contains[*declaration*](dcl.pre#nt:declaration "9.1Preamble[dcl.pre]")*s* in its [*namespace-body*](#nt:namespace-body "9.9.2.1General[namespace.def.general]") and a[*namespace-definition*](#nt:namespace-definition "9.9.2.1General[namespace.def.general]") is itself a [*declaration*](dcl.pre#nt:declaration "9.1Preamble[dcl.pre]"), it
follows that [*namespace-definition*](#nt:namespace-definition "9.9.2.1General[namespace.def.general]")*s* can be nested[.](#general-3.sentence-1)
[*Example [1](#general-example-1)*: namespace Outer {int i; namespace Inner {void f() { i++; } // Outer::iint i; void g() { i++; } // Inner::i}} — *end example*]
[4](#general-4)
[#](http://github.com/Eelis/draft/tree/9adde4bc1c62ec234483e63ea3b70a59724c745a/source/declarations.tex#L8305)
If the optional initial inline keyword appears in a[*namespace-definition*](#nt:namespace-definition "9.9.2.1General[namespace.def.general]") for a particular namespace, that namespace is
declared to be an [*inline namespace*](#def:namespace,inline "9.9.2.1General[namespace.def.general]")[.](#general-4.sentence-1)
The inline keyword may be
used on a [*namespace-definition*](#nt:namespace-definition "9.9.2.1General[namespace.def.general]") that extends a namespace
only if it was previously used on the [*namespace-definition*](#nt:namespace-definition "9.9.2.1General[namespace.def.general]") that initially declared the [*namespace-name*](#nt:namespace-name "9.9.2.1General[namespace.def.general]") for that namespace[.](#general-4.sentence-2)
[5](#general-5)
[#](http://github.com/Eelis/draft/tree/9adde4bc1c62ec234483e63ea3b70a59724c745a/source/declarations.tex#L8313)
The optional [*attribute-specifier-seq*](dcl.attr.grammar#nt:attribute-specifier-seq "9.13.1Attribute syntax and semantics[dcl.attr.grammar]") in a [*named-namespace-definition*](#nt:named-namespace-definition "9.9.2.1General[namespace.def.general]") appertains to the namespace being defined or extended[.](#general-5.sentence-1)
[6](#general-6)
[#](http://github.com/Eelis/draft/tree/9adde4bc1c62ec234483e63ea3b70a59724c745a/source/declarations.tex#L8318)
Members of an inline namespace can be used in most respects as though they were members
of the innermost enclosing namespace[.](#general-6.sentence-1)
Specifically, the inline namespace and its enclosing
namespace are both added to the set of associated namespaces used in[argument-dependent lookup](basic.lookup.argdep "6.5.4Argument-dependent name lookup[basic.lookup.argdep]") whenever one of them is,
and a [*using-directive*](namespace.udir#nt:using-directive "9.9.4Using namespace directive[namespace.udir]") ([[namespace.udir]](namespace.udir "9.9.4Using namespace directive")) that names the inline
namespace is implicitly inserted into the enclosing namespace as for an unnamed
namespace ([[namespace.unnamed]](#namespace.unnamed "9.9.2.2Unnamed namespaces"))[.](#general-6.sentence-2)
Furthermore, each
member of the inline namespace can subsequently be partially
specialized ([[temp.spec.partial]](temp.spec.partial "13.7.6Partial specialization")), explicitly
instantiated ([[temp.explicit]](temp.explicit "13.9.3Explicit instantiation")), or explicitly specialized ([[temp.expl.spec]](temp.expl.spec "13.9.4Explicit specialization")) as
though it were a member of the enclosing namespace[.](#general-6.sentence-3)
Finally, looking up a name in the
enclosing namespace via explicit qualification ([[namespace.qual]](namespace.qual "6.5.5.3Namespace members")) will include
members of the inline namespace even if
there are declarations of that name in the enclosing namespace[.](#general-6.sentence-4)
[7](#general-7)
[#](http://github.com/Eelis/draft/tree/9adde4bc1c62ec234483e63ea3b70a59724c745a/source/declarations.tex#L8334)
These properties are transitive: if a namespace N contains an inline namespaceM, which in turn contains an inline namespace O, then the members ofO can be used as though they were members of M or N[.](#general-7.sentence-1)
The [*inline namespace set*](#def:inline_namespace_set "9.9.2.1General[namespace.def.general]") of N is the transitive closure of all
inline namespaces in N[.](#general-7.sentence-2)
[8](#general-8)
[#](http://github.com/Eelis/draft/tree/9adde4bc1c62ec234483e63ea3b70a59724c745a/source/declarations.tex#L8341)
A [*nested-namespace-definition*](#nt:nested-namespace-definition "9.9.2.1General[namespace.def.general]") with an[*enclosing-namespace-specifier*](#nt:enclosing-namespace-specifier "9.9.2.1General[namespace.def.general]") E,[*identifier*](lex.name#nt:identifier "5.11Identifiers[lex.name]") I and[*namespace-body*](#nt:namespace-body "9.9.2.1General[namespace.def.general]") B is equivalent tonamespace E { inlineopt namespace I { B } } where the optional inline is present if and only if
the [*identifier*](lex.name#nt:identifier "5.11Identifiers[lex.name]") I is preceded by inline[.](#general-8.sentence-1)
[*Example [2](#general-example-2)*: namespace A::inline B::C {int i;}
The above has the same effect as:namespace A {inline namespace B {namespace C {int i; }}}
— *end example*]
#### [9.9.2.2](#namespace.unnamed) Unnamed namespaces [[namespace.unnamed]](namespace.unnamed)
[1](#namespace.unnamed-1)
[#](http://github.com/Eelis/draft/tree/9adde4bc1c62ec234483e63ea3b70a59724c745a/source/declarations.tex#L8373)
An [*unnamed-namespace-definition*](#nt:unnamed-namespace-definition "9.9.2.1General[namespace.def.general]") behaves as if it were
replaced by
inlineopt namespace *unique* { /* empty body */ }
using namespace *unique* ;
namespace *unique* { [*namespace-body*](#nt:namespace-body "9.9.2.1General[namespace.def.general]") }
whereinline appears if and only if it appears in the[*unnamed-namespace-definition*](#nt:unnamed-namespace-definition "9.9.2.1General[namespace.def.general]") and all occurrences of *unique* in a translation unit are replaced by
the same identifier, and this identifier differs from all other
identifiers in the program[.](#namespace.unnamed-1.sentence-1)
The optional [*attribute-specifier-seq*](dcl.attr.grammar#nt:attribute-specifier-seq "9.13.1Attribute syntax and semantics[dcl.attr.grammar]") in the [*unnamed-namespace-definition*](#nt:unnamed-namespace-definition "9.9.2.1General[namespace.def.general]") appertains to *unique*[.](#namespace.unnamed-1.sentence-2)
[*Example [1](#namespace.unnamed-example-1)*: namespace { int i; } // *unique*::ivoid f() { i++; } // *unique*::i++namespace A {namespace {int i; // A::*unique*::iint j; // A::*unique*::j}void g() { i++; } // A::*unique*::i++}using namespace A;void h() { i++; // error: *unique*::i or A::*unique*::i A::i++; // A::*unique*::i j++; // A::*unique*::j} — *end example*]