C++学习笔记(5)

C++ Primer Chapter 7

Class 类 初识

  • class定义结束有分号
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
class A {
 public:
    //成员变量
    int a_;
    //构造器constructor
    //               |initialization list初始化列表
    A(int value) : a_(a) {}

    //成员函数
    void funcA(){
        cout << a_ << endl;
    }
};

int main(){
    A a(10);
    A a1 = A(10);
    A a2 = 10;
    return 0;
}

类权限控制 access control

  • public,公开访问权限

  • private只能在类内使用,通过friend可以无视权限,但会破坏封装原则。

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
#include<iostream>
using std::cout;
using std::endl;

class ParentClass{
    //declaration
    friend void ffunc(ParentClass pclass);
 private:
    int a = 1;
};

//definition
void ffunc(ParentClass pclass){
    cout << pclass.a << endl;
}

int main(){
    ParentClass pclass;
    ffunc(pclass);
    return 0;
}
  • protected
  • const
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
void func1() const{
    //  在func1的scope内的对象都是const的,不能被改变
    this.a_ = 10; //❌,除非 a_ 变量为 mutable
}

//返回一个可变
OwnClass& func2(int arg){
    //code
    return *this;
}

//返回一个可变的OwnClass对象(引用),且函数内部不发生对象的改变
OwnClass& func2 const(int arg){
    //code
    return *this;
}

//返回一个不可变的OwnClass对象(引用),且函数内部不发生对象的改变
const OwnClass& func2 const(int arg){
    //code
    return *this;
}

返回*this

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12

//返回拷贝
OwnClass func1(){
    //code
    return *this;
}

//返回本身对象
OwnClass& func2(){
    //code
    return *this;
}

初始化列表

  • 能使用初始化列表尽量用(效率更高),使用assignment是先进行初始化再进行assignment。
  • const的成员变量只能使用初始化
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
class A {
 public:
    int a_;
    int b_;
    int c_;
//                    |initialization list
    A(int a, int b) : a_(a), b_(b), c_(c) {
        this->a_ = a; //assignment
    }

    //成员函数
    void funcA(){
        cout << a_ << endl;
    }
};

委托构造器 delegate constructor

代码复用,减少代码量

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
class SalesData{
public:
    int a_;
    bool b_;
    long c_;

    SalesData(int a, bool b, long c) : a_(a), b_(b), c_(c){}

    SalesData(int a, bool b) : SalesData(a, b, 100){}

    SalesData(int a) : SalesData(a, true, 100){}
}

explict显式

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
class SalesData{
public:
    int a_;
    bool b_;
    long c_;

    SalesData(int a, bool b, long c) : a_(a), b_(b), c_(c){}

    SalesData(int a, bool b) : SalesData(a, b, 100){}

    explict SalesData(int a) : SalesData(a, true, 100){}
}

void func(SalesData sales_data){
    cout << "!" << endl;
}

int main(){
    func(20);//会报错,因为有explicit关键字
    //若没有explicit,则会隐式地创建一个对象SalesData tmp(20);
}

default 构造

1
SalesData() = default;
  • 对于类内的成员变量,必须要有一个default构造器,否则在被其他类调用默认构造方法的时候会出错
  • 一个类有了自己写的构造方法后编译器会添加delete,即删除默认构造器;
  • 最佳实践:在定义的构造器后添加默认构造器
1
2
3
ClassName(int a, bool b): a_(a), b_(b){}
//behind other constructor
ClassName() = default;

static 成员

  • static 成员变量 不随对象的存在而存在,随整个程序的存在而存在,程序销毁才销毁
  • static 不能使用this索引到
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
class A {
public:
    int a_;
    static int static_a;

    A(int a): a_(a){}

    static void func(){
        cout << this->a_ << endl;//❌ static function不依附于任何对象,不能用this寻址
        cout << static_a << endl;//✔️ 
    }
}

int A::static_a = 10;//static 成员变量不属于任何对象,所以只能在类body外进行定义和初始化
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
#include<iostream>
using std::cout;
using std::endl;

class MyClass{
public:
    int a_; //正常成员变量

    static int static_a; //静态成员变量
    static void func(){ //静态成员函数
        cout << "static method" << endl;
    }

    MyClass(int a): a_(a){} //构造方法
    MyClass() = default; //默认构造方法
};

int MyClass::static_a = 10; //初始化静态变量

int main(){
    MyClass myclass;
    cout << MyClass::static_a << endl; //通过scope符引用静态变量
    cout << myclass.static_a << endl; //通过dot引用
    myclass.func();  //通过dot调用静态方法

    return 0;
}