c++总复习

时间:2024-12-15 13:33:45
  1. C++ 中多态性在实际项目中的应用场景
    • 图形绘制系统
      • 描述:在一个图形绘制软件中,可能有多种图形,如圆形、矩形、三角形等。这些图形都有一个共同的操作,比如绘制(draw)。通过多态性,可以定义一个基类Shape,其中有一个纯虚函数draw。然后,CircleRectangleTriangle等派生类分别实现自己的draw函数。
      • 代码示例
class Shape {
public:
    virtual void draw() = 0;
};
class Circle : public Shape {
public:
    void draw() override {
        // 绘制圆形的具体代码
        std::cout << "Drawing a circle." << std::endl;
    }
};
class Rectangle : public Shape {
public:
    void draw() override {
        // 绘制矩形的具体代码
        std::cout << "Drawing a rectangle." << std::endl;
    }
};
  • 优势:当需要绘制一系列图形时,可以将这些图形对象存储在一个Shape指针数组中。然后通过遍历数组,调用每个对象的draw函数,而不需要为每种图形单独编写绘制代码。这样可以使代码结构更加清晰,易于维护和扩展。如果要添加新的图形,只需要创建一个新的派生类并实现draw函数即可。
  • 设备驱动程序开发
    • 描述:在操作系统的设备驱动开发中,不同的设备(如打印机、扫描仪、硬盘等)有不同的操作方式。可以定义一个基类Device,其中有虚函数如openclosereadwrite等。不同设备的驱动程序类(如PrinterScannerHardDisk)作为派生类,根据设备的具体特性实现这些虚函数。
    • 代码示例(简化)
class Device {
public:
    virtual bool open() = 0;
    virtual bool close() = 0;
    virtual size_t read(char* buffer, size_t size) = 0;
    virtual size_t write(const char* data, size_t size) = 0;
};
class Printer : public Device {
public:
    bool open() override {
        // 打开打印机的具体代码
        return true;
    }
    bool close() override {
        // 关闭打印机的具体代码
        return true;
    }
    size_t read(char* buffer, size_t size) override {
        // 打印机一般不进行读取操作,返回0
        return 0;
    }
    size_t write(const char* data, size_t size) override {
        // 打印数据的具体代码
        return size;
    }
};
  • 优势:操作系统可以使用统一的接口来处理不同的设备。例如,在一个文件读写操作的函数中,它可以接收一个Device指针。根据实际传入的是打印机、扫描仪还是硬盘的对象指针,会调用相应设备的readwrite函数。这使得操作系统的设备管理模块能够以一种通用的方式与各种设备进行交互,提高了代码的复用性和可维护性。
  • 游戏开发中的角色行为
    • 描述:在游戏中,不同的角色有不同的行为。例如,战士、法师、刺客等角色都有攻击(attack)行为,但他们的攻击方式不同。可以定义一个基类Character,其中有一个虚函数attack。每个角色类(如WarriorMageAssassin)作为派生类,实现自己的attack函数。
    • 代码示例(简化)
class Character {
public:
    virtual void attack() = 0;
};
class Warrior : public Character {
public:
    void attack() override {
        // 战士攻击的具体代码,可能是近身物理攻击
        std::cout << "Warrior attacks with a sword." << std::endl;
    }
};
class Mage : public Character {
public:
    void attack() override {
        // 法师攻击的具体代码,可能是释放魔法
        std::cout << "Mage casts a spell." << std::endl;
    }
};
  • 优势:游戏中的战斗场景可以通过一个Character指针数组来管理角色。在战斗循环中,遍历数组并调用每个角色的attack函数,实现不同角色的攻击行为。这样可以方便地添加新的角色类型,并且在游戏逻辑处理上更加灵活,代码的组织结构也更加合理。

  1. C++ 中面向对象编程实现数据隐藏的方法
    • 使用类的访问限定符(private、protected、public)
      • 描述:在 C++ 中,private访问限定符用于限制类的成员(数据成员和成员函数)只能在类的内部访问。例如,定义一个Person类,其中有一个age数据成员,将其设为private,外部代码就不能直接访问这个成员。
      • 代码示例
class Person {
private:
    int age;
public:
    void setAge(int a) {
        if (a > 0) {
            age = a;
        }
    }
    int getAge() {
        return age;
    }
};
  • 原理:通过将age设为private,只能通过类提供的setAgegetAge函数来间接访问和修改age的值。这样可以在setAge函数中添加数据验证逻辑,保证age的值符合一定的规则(如年龄不能为负数)。外部代码无法绕过这些函数直接操作age,从而实现了数据隐藏和封装。
  • 使用友元函数和友元类(谨慎使用)
    • 描述:友元函数和友元类可以访问类的privateprotected成员。虽然这看起来好像破坏了数据隐藏,但在某些特定情况下是有用的。例如,定义一个Date类和一个DateUtil类,DateUtil类中的某些函数可能需要直接访问Date类的内部成员来进行日期计算等操作。
    • 代码示例
class Date {
private:
    int year;
    int month;
    int day;
    friend class DateUtil;
};
class DateUtil {
public:
    bool isLeapYear(const Date& d) {
        // 直接访问Date类的year成员进行判断
        if ((d.year % 4 == 0 && d.year % 100!= 0) || (d.year % 400 == 0)) {
            return true;
        }