在线文档教程
C++
语言 | Language

Non-static member functions

非静态成员函数

非静态成员函数是在成员规格类的静态或朋友说明符。

二次

class S { int mf1( // non-static member function declaration void mf2() volatile, mf3() &&; // can be cv-qualified and reference-qualified int mf4() const { return data; } // can be defined inline virtual void mf5() final; // can be virtual, can use final/override S() : data(12) {} // constructors are member functions too int data; }; int S::mf1() { return 7; } // if not defined inline, has to be defined at namespace

二次

任何函数声明允许使用仅对非静态成员函数可用的附加语法元素:最终和覆盖说明符,纯规范,cv-限定符,ref-限定符,以及成员初始化列表...

可以调用X类的非静态成员函数。

1%29用于使用类成员访问运算符的X类型对象

2%29用于类的对象导出从X

3%29直接从X的成员函数体内

4%29直接从从X导出的类的成员函数体内

在任何其他类型的对象上调用X类的成员函数将调用未定义的行为。

在X的非静态成员函数的主体中,任何ID-表达式e%28 e.。将解析为X的非类型非静态成员或X基类的标识符%29转换为成员访问表达式。(*this).E%28,除非它已成为成员访问表达式%29的一部分。这在模板定义上下文中不会发生,因此名称可能必须以前缀。this->明示成相依...

二次

struct S { int n; void f( }; void S::f() { n = 1; // transformed to (*this).n = 1; } int main() { S s1, s2; s1.f( // changes s1.n }

二次

在X的非静态成员函数的主体中,任何解析为静态成员的非限定id、枚举器或嵌套类型X或X的基类都被转换为相应的限定-id。

二次

struct S { static int n; void f( }; void S::f() { n = 1; // transformed to S::n = 1; } int main() { S s1, s2; s1.f( // changes S::n }

二次

Const-、Volatile-和ref-限定成员函数

非静态成员函数可以使用Const、Volatile或Const挥发性限定符%28声明。此限定符出现在功能声明29%。不同的是,cv限定的函数有不同的类型,因此可能会使彼此超载。

在cv限定函数的主体中,这指针是cv限定的,例如在const成员函数,通常只能调用其他Const成员函数。%28a非连续成员函数仍可被调用,如果康斯特[医]铸造应用,或通过不涉及以下内容的访问路径应用这.%29

二次

#include <vector> struct Array { std::vector<int> data; Array(int sz) : data(sz) {} // const member function int operator[](int idx) const { // this has type const Array* return data[idx]; // transformed to (*this).data[idx]; } // non-const member function int& operator[](int idx) { // this has type Array* return data[idx]; // transformed to (*this).data[idx] } }; int main() { Array a(10 a[1] = 1; // OK: the type of a[1] is int& const Array ca(10 ca[1] = 2; // Error: the type of ca[1] is int }

二次

A non-static member function can be declared with no ref-qualifier, with an lvalue ref-qualifier (the token & after the function name) or the rvalue ref-qualifier (the token && after the function name). During overload resolution, non-static cv-qualified member function of class X is treated as follows: no ref-qualifier: the implicit object parameter has type lvalue reference to cv-qualified X and is additionally allowed to bind rvalue implied object argument lvalue ref-qualifier: the implicit object parameter has type lvalue reference to cv-qualified X rvalue ref-qualifier: the implicit object parameter has type rvalue reference to cv-qualified X #include struct S { void f() & { std::cout << "lvalue\n"; } void f() &&{ std::cout << "rvalue\n"; } }; int main(){ S s; s.f( // prints "lvalue" std::move(s).f( // prints "rvalue" S().f( // prints "rvalue" } Note: unlike cv-qualification, ref-qualification does not change the properties of the this pointer: within a rvalue ref-qualified function, *this remains an lvalue expression.(since C++11)

  • 没有ref-限定符:隐式对象参数具有对cv限定X的类型lvalue引用,并且还允许绑定rvalue隐含对象参数。

  • lvalue ref-限定符:隐式对象参数具有对cv限定X的lvalue引用类型。

  • rvalue ref-限定符:隐式对象参数具有对cv限定X的类型rvalue引用。

#包括<iostream>结构S{voidf%28%29&{std::cout<<“lvalue\n”;}voidf%28%29&{std:cout<<“rvalue\n”};int main%28%29{s;S.F%28%29;//打印“lvalue”std::Move%28s%29。F%28%29;//打印“rvalue”S%28%29。F%28%29;//打印“rvalue”}

注意:与cv-资质不同,ref-资质不会更改这指针:在rvalue ref限定函数中,*this仍然是一个lvalue表达式。

%28自C++11%29

虚纯虚函数

可以声明非静态成员函数。虚拟纯虚拟.见虚函数和抽象类关于细节。

特殊成员函数

建设者和破坏者是对声明%28使用特殊语法的非公共成员函数,有关详细信息,请参阅其页%29。

一些成员函数是特制在某些情况下,它们是由编译器定义的,即使用户没有定义它们。它们是:

  • 默认构造函数

  • 复制构造函数

  • 移动构造函数%28自C++11%29

  • 复制赋值算子

  • 移动赋值算子%28自C++11%29

  • 破坏者

特殊成员函数是唯一可以违约,也就是说,使用= default有关详细信息,请参阅其页面,而不是函数体%28。

二次

#include <iostream> #include <string> #include <utility> #include <exception> struct S { int data; // simple converting constructor (declaration) S(int val // simple explicit constructor (declaration) explicit S(std::string str // const member function (definition) virtual int getData() const { return data; } }; // definition of the constructor S::S(int val) : data(val) { std::cout << "ctor1 called, data = " << data << '\n'; } // this constructor has a catch clause S::S(std::string str) try : data(std::stoi(str)) { std::cout << "ctor2 called, data = " << data << '\n'; } catch(const std::exception&) { std::cout << "ctor2 failed, string was '" << str << "'\n"; throw; // ctor's catch clause should always rethrow } struct D : S { int data2; // constructor with a default argument D(int v1, int v2 = 11) : S(v1), data2(v2) {} // virtual member function int getData() const override { return data*data2; } // lvalue-only assignment operator D& operator=(D other) & { std::swap(other.data, data std::swap(other.data2, data2 return *this; } }; int main() { D d1 = 1; S s2("2" try { S s3("not a number" } catch(const std::exception&) {} std::cout << s2.getData() << '\n'; D d2(3, 4 d2 = d1; // OK: assignment to lvalue // D(5) = d1; // ERROR: no suitable overload of operator= }

二次

产出:

二次

ctor1 called, data = 1 ctor2 called, data = 2 ctor2 failed, string was 'not a number' 2 ctor1 called, data = 3

二次

另见

  • 数据成员

  • 静态数据成员

© cppreference.com

在CreativeCommonsAttribution下授权-ShareAlike未移植许可v3.0。

http://en.cppreference.com/w/cpp/language/Members[医]功能