C++

C++ 知识量:19 - 82 - 316

7.1 定义抽象数据类型><

抽象类- 7.1.1 -

在C++中,可以使用抽象类(abstract class)定义抽象数据类型。抽象类是一种只能被继承不能被实例化的类,它用于定义抽象方法(没有实现的方法)。子类必须实现所有父类中的抽象方法,否则它们也将被视为抽象类。

以下是一个简单的例子,展示了如何定义一个名为Shape的抽象类:

#include <iostream>  
using namespace std;  
  
// 定义抽象类Shape  
class Shape {  
public:  
    // 定义抽象方法printArea  
    virtual void printArea() const = 0;  
};  
  
// 定义派生类Rectangle,并实现printArea方法  
class Rectangle : public Shape {  
public:  
    Rectangle(double w, double h) : width(w), height(h) {}  
    void printArea() const override {  
        cout << "The area of the rectangle is " << width * height << endl;  
    }  
private:  
    double width, height;  
};  
  
// 定义派生类Circle,并实现printArea方法  
class Circle : public Shape {  
public:  
    Circle(double r) : radius(r) {}  
    void printArea() const override {  
        cout << "The area of the circle is " << 3.14 * radius * radius << endl;  
    }  
private:  
    double radius;  
};  
  
int main() {  
    Rectangle rect(10, 5); // 定义Rectangle对象rect,并传入参数10和5  
    Circle cir(10); // 定义Circle对象cir,并传入参数10  
    // 调用printArea方法分别打印矩形和圆的面积  
    rect.printArea(); // 输出"The area of the rectangle is 50"  
    cir.printArea(); // 输出"The area of the circle is 314.16"  
    return 0;  
}

在上面的例子中,Shape是一个抽象类,它定义了一个抽象方法printArea。Rectangle和Circle是两个派生类,它们分别实现了printArea方法。在main函数中,定义了一个Rectangle对象rect和一个Circle对象cir,并调用了它们的printArea方法来打印它们的面积。

隐式形参this- 7.1.2 -

在C++中,每一个非静态成员函数都有一个隐式的形参,即this指针。this指针是一个指向调用对象自身的指针,它允许成员函数访问调用对象的非静态成员。

对于非静态成员函数,编译器会自动生成一个this指针,并将其作为函数的第一个参数传递。这个this指针的类型是调用对象的类型,而不是函数本身的类型。

例如,对于下面的代码:

class MyClass {  
public:  
    void myFunction(int x) {  
        // 使用this指针访问对象的非静态成员  
        this->myMember = x;  
    }  
private:  
    int myMember;  
};

在这个例子中,myFunction是一个非静态成员函数,它接受一个整数参数x。在函数体中,使用this指针来访问对象的非静态成员myMember。由于myFunction是一个非静态成员函数,编译器会自动生成一个this指针,并将其作为函数的第一个参数传递。可以通过this->myMember = x;来访问和修改对象的非静态成员myMember。

需要注意的是,this指针是只读的,不能被修改。同时,由于this指针是隐式的,不能在函数参数列表中显式地指定它。

const成员函数- 7.1.3 -

在C++中,const成员函数是一种特殊的成员函数,它可以在const对象上调用,并且保证不会修改对象的状态。

const成员函数的声明语法是在函数参数列表后面加上const关键字。例如:

class MyClass {  
public:  
    void myFunction() const; // const成员函数声明  
};

在const成员函数中,不能修改任何成员变量或调用任何非const成员函数。如果违反了这个规定,编译器将会报错。

const成员函数主要用于以下几个方面:

  • 保证对象的完整性:当一个对象被const修饰时,可以保证它不会被修改,从而保证了对象的完整性。

  • 实现多态性:const成员函数可以用于实现多态性。在基类的const成员函数中调用虚函数时,会自动调用派生类的const成员函数,从而实现了多态性。

  • 提高代码的可读性和可维护性:const成员函数可以清楚地表明该函数不会修改对象的状态,从而提高了代码的可读性和可维护性。

类作用域- 7.1.4 -

在C++中,类作用域(Class Scope)是指类的成员变量和成员函数的访问范围。在一个类中声明的变量和函数只在该类内部可见,这就是类作用域。

在类外部,只能通过类的对象来访问类的成员变量和成员函数。在类内部,可以直接访问类的成员变量和成员函数,无需使用对象。

类作用域的规则如下:

  1. 类成员变量和成员函数只在该类内部可见。

  2. 在类内部可以直接访问类的成员变量和成员函数,无需使用对象。

  3. 在类外部,只能通过类的对象来访问类的成员变量和成员函数。

  4. 如果在类外部定义类的成员函数,必须使用作用域解析运算符(::)来指定该函数属于哪个类。

  5. 类的静态成员变量和静态成员函数属于类本身,而不是类的对象,因此可以在类外部直接访问。

以下是一个简单的示例代码:

#include <iostream>  
  
class MyClass {  
public:  
    int myVar; // 类成员变量  
    void myFunc() { // 类成员函数  
        std::cout << "This is a class member function." << std::endl;  
    }  
};  
  
int main() {  
    MyClass obj; // 创建类的对象  
    obj.myVar = 10; // 访问类的成员变量  
    obj.myFunc(); // 调用类的成员函数  
    return 0;  
}

定义一个返回this对象的函数- 7.1.5 -

在C++中,可以使用->或者*操作符从成员函数中返回当前对象的指针。下面是一个定义一个返回this对象的函数的示例:

class MyClass {  
public:  
    MyClass* getThis() {  
        return this;  
    }  
};

在这个示例中,getThis()函数返回当前对象的指针。this是一个指向当前对象的指针,它可以在成员函数中使用。通过返回this指针,可以实现一个返回当前对象的函数。

构造函数- 7.1.6 -

C++中的构造函数是一种特殊的成员函数,它在创建对象时自动调用。构造函数的名称与类的名称相同,并且它不返回任何类型,连void也没有。以下是构造函数的定义形式:

class ClassName {  
    public:  
        ClassName() {   
            // 函数体   
        }  
};

在上面的例子中,ClassName是一个类的名称,而ClassName()就是该类的构造函数。当创建ClassName类的对象时,构造函数将自动执行。

构造函数可以有参数,例如:

class ClassName {  
    public:  
        ClassName(int a) {   
            // 函数体   
        }  
};

在这个例子中,构造函数ClassName(int a)接受一个int类型的参数。当创建ClassName类的对象时,需要向构造函数传递一个int类型的参数。

构造函数的另一个重要特性是它可以重载。这意味着可以创建多个同名的构造函数,只要它们的参数列表不同。例如:

class ClassName {  
    public:  
        ClassName() {   
            // 函数体   
        }  
        ClassName(int a) {   
            // 函数体   
        }  
};

在这个例子中,有两个同名的构造函数:ClassName()和ClassName(int a)。一个是无参构造函数,另一个是接受一个int类型参数的构造函数。

析构函数- 7.1.7 -

析构函数(destructor)是一种特殊的成员函数,用于在销毁对象时进行清理工作。在C++中,析构函数的名称为类名前加上波浪号(~)。析构函数没有返回类型,也没有参数,它主要用于释放对象使用的资源,如内存、文件句柄等。

析构函数的调用时机通常是在对象生命周期结束时,例如当对象离开其作用域或被手动删除时。析构函数执行完成后,对象将被销毁。

以下是一个示例,演示如何在C++中声明和定义析构函数:

class MyClass {  
public:  
    // 构造函数  
    MyClass() {  
        // 构造函数的实现  
    }  
  
    // 析构函数  
    ~MyClass() {  
        // 析构函数的实现,用于释放资源  
    }  
};

需要注意的是,析构函数的调用顺序通常与构造函数的调用顺序相反。即先构造的对象后被销毁,先构造的对象后被销毁。此外,析构函数也可以重载,以便在销毁对象时执行不同的操作。