109 lines
4.8 KiB
Markdown
109 lines
4.8 KiB
Markdown
[class.name]
|
||
|
||
# 11 Classes [[class]](./#class)
|
||
|
||
## 11.3 Class names [class.name]
|
||
|
||
[1](#1)
|
||
|
||
[#](http://github.com/Eelis/draft/tree/9adde4bc1c62ec234483e63ea3b70a59724c745a/source/classes.tex#L408)
|
||
|
||
A class definition introduces a new type[.](#1.sentence-1)
|
||
|
||
[*Example [1](#example-1)*:
|
||
|
||
struct X { int a; };struct Y { int a; };
|
||
X a1;
|
||
Y a2;int a3; declares three variables of three different types[.](#1.sentence-2)
|
||
|
||
This implies thata1 = a2; // error: Y assigned to X a1 = a3; // error: int assigned to X are type mismatches, and thatint f(X);int f(Y);declare overloads ([[over]](over "12 Overloading")) named f and not
|
||
simply a single function f twice[.](#1.sentence-3)
|
||
|
||
For the same reason,struct S { int a; };struct S { int a; }; // error: double definition is ill-formed because it defines S twice[.](#1.sentence-4)
|
||
|
||
â *end example*]
|
||
|
||
[2](#2)
|
||
|
||
[#](http://github.com/Eelis/draft/tree/9adde4bc1c62ec234483e63ea3b70a59724c745a/source/classes.tex#L438)
|
||
|
||
[*Note [1](#note-1)*:
|
||
|
||
It can be necessary to use an [*elaborated-type-specifier*](dcl.type.elab#nt:elaborated-type-specifier "9.2.9.5 Elaborated type specifiers [dcl.type.elab]") to refer to a class
|
||
that belongs to a scope in which its name is also bound to
|
||
a variable, function, or enumerator ([[basic.lookup.elab]](basic.lookup.elab "6.5.6 Elaborated type specifiers"))[.](#2.sentence-1)
|
||
|
||
[*Example [2](#example-2)*: struct stat {// ...};
|
||
|
||
stat gstat; // use plain stat to define variableint stat(struct stat*); // stat now also names a functionvoid f() {struct stat* ps; // struct prefix needed to name struct stat stat(ps); // call stat function} â *end example*]
|
||
|
||
An [*elaborated-type-specifier*](dcl.type.elab#nt:elaborated-type-specifier "9.2.9.5 Elaborated type specifiers [dcl.type.elab]") can also be used to declare
|
||
an [*identifier*](lex.name#nt:identifier "5.11 Identifiers [lex.name]") as a [*class-name*](class.pre#nt:class-name "11.1 Preamble [class.pre]")[.](#2.sentence-2)
|
||
|
||
[*Example [3](#example-3)*: struct s { int a; };
|
||
|
||
void g() {struct s; // hide global struct s with a block-scope declaration s* p; // refer to local struct sstruct s { char* p; }; // define local struct sstruct s; // redeclaration, has no effect} â *end example*]
|
||
|
||
Such declarations allow definition of classes that refer to each other[.](#2.sentence-3)
|
||
|
||
[*Example [4](#example-4)*: class Vector;
|
||
|
||
class Matrix {// ...friend Vector operator*(const Matrix&, const Vector&);};
|
||
|
||
class Vector {// ...friend Vector operator*(const Matrix&, const Vector&);};
|
||
|
||
Declaration of friends is described in [[class.friend]](class.friend "11.8.4 Friends"),
|
||
operator functions in [[over.oper]](over.oper "12.4 Overloaded operators")[.](#2.sentence-4)
|
||
|
||
â *end example*]
|
||
|
||
â *end note*]
|
||
|
||
[3](#3)
|
||
|
||
[#](http://github.com/Eelis/draft/tree/9adde4bc1c62ec234483e63ea3b70a59724c745a/source/classes.tex#L497)
|
||
|
||
[*Note [2](#note-2)*:
|
||
|
||
An [*elaborated-type-specifier*](dcl.type.elab#nt:elaborated-type-specifier "9.2.9.5 Elaborated type specifiers [dcl.type.elab]") ([[dcl.type.elab]](dcl.type.elab "9.2.9.5 Elaborated type specifiers")) can also
|
||
be used as a [*type-specifier*](dcl.type.general#nt:type-specifier "9.2.9.1 General [dcl.type.general]") as part of a declaration[.](#3.sentence-1)
|
||
|
||
It
|
||
differs from a class declaration in that it can refer to
|
||
an existing class of the given name[.](#3.sentence-2)
|
||
|
||
â *end note*]
|
||
|
||
[*Example [5](#example-5)*: struct s { int a; };
|
||
|
||
void g(int s) {struct s* p = new struct s; // global s p->a = s; // parameter s} â *end example*]
|
||
|
||
[4](#4)
|
||
|
||
[#](http://github.com/Eelis/draft/tree/9adde4bc1c62ec234483e63ea3b70a59724c745a/source/classes.tex#L517)
|
||
|
||
[*Note [3](#note-3)*:
|
||
|
||
The declaration of a class name takes effect immediately after the[*identifier*](lex.name#nt:identifier "5.11 Identifiers [lex.name]") is seen in the class definition or[*elaborated-type-specifier*](dcl.type.elab#nt:elaborated-type-specifier "9.2.9.5 Elaborated type specifiers [dcl.type.elab]")[.](#4.sentence-1)
|
||
|
||
[*Example [6](#example-6)*:
|
||
|
||
class A * A; first specifies A to be the name of a class and then redefines
|
||
it as the name of a pointer to an object of that class[.](#4.sentence-2)
|
||
|
||
This means that
|
||
the elaborated form class A must be used to refer to the
|
||
class[.](#4.sentence-3)
|
||
|
||
Such artistry with names can be confusing and is best avoided[.](#4.sentence-4)
|
||
|
||
â *end example*]
|
||
|
||
â *end note*]
|
||
|
||
[5](#5)
|
||
|
||
[#](http://github.com/Eelis/draft/tree/9adde4bc1c62ec234483e63ea3b70a59724c745a/source/classes.tex#L534)
|
||
|
||
A [*simple-template-id*](temp.names#nt:simple-template-id "13.3 Names of template specializations [temp.names]") is only a [*class-name*](class.pre#nt:class-name "11.1 Preamble [class.pre]") if its [*template-name*](temp.names#nt:template-name "13.3 Names of template specializations [temp.names]") names a class template[.](#5.sentence-1)
|