MST

星途 面试题库

面试题:C++中重写拷贝构造函数时浅拷贝与深拷贝对性能的影响

在C++中,重写拷贝构造函数时,浅拷贝和深拷贝是两种常见的方式。请详细阐述浅拷贝和深拷贝的区别,以及它们在性能方面各自的优缺点。同时,给出一个简单的类示例,分别展示浅拷贝和深拷贝的实现,并分析在不同场景下应如何选择。
15.1万 热度难度
编程语言C++

知识考点

AI 面试

面试题答案

一键面试

浅拷贝和深拷贝的区别

  1. 浅拷贝: 浅拷贝只是简单地复制对象中的成员变量的值。对于指针类型的成员变量,浅拷贝会使新对象和原对象的指针指向同一块内存地址。这意味着如果其中一个对象对该内存进行释放或修改,会影响到另一个对象。
  2. 深拷贝: 深拷贝不仅复制对象中的成员变量的值,对于指针类型的成员变量,会在堆上重新分配一块新的内存,并将原对象指针所指向的内容复制到新分配的内存中。这样新对象和原对象的指针指向不同的内存地址,相互独立,对一个对象的操作不会影响另一个对象。

性能方面的优缺点

  1. 浅拷贝
    • 优点:性能较高,因为它只需要简单地复制成员变量的值,不需要额外的内存分配和数据复制操作。
    • 缺点:存在内存管理问题,可能导致悬空指针、内存泄漏等问题,因为多个对象可能共享同一块内存。
  2. 深拷贝
    • 优点:内存管理更安全,避免了多个对象共享同一块内存带来的问题。
    • 缺点:性能较低,因为需要额外的内存分配和数据复制操作,特别是当复制的对象较大或包含复杂数据结构时,开销较大。

类示例

#include <iostream>
#include <cstring>

class MyString {
private:
    char* str;
    int length;

public:
    // 构造函数
    MyString(const char* s = nullptr) {
        if (s == nullptr) {
            length = 0;
            str = new char[1];
            str[0] = '\0';
        } else {
            length = strlen(s);
            str = new char[length + 1];
            strcpy(str, s);
        }
    }

    // 浅拷贝构造函数
    MyString(const MyString& other) {
        length = other.length;
        str = other.str;
    }

    // 深拷贝构造函数
    MyString(const MyString& other) {
        length = other.length;
        str = new char[length + 1];
        strcpy(str, other.str);
    }

    // 析构函数
    ~MyString() {
        delete[] str;
    }

    void print() {
        std::cout << str << std::endl;
    }
};

不同场景下的选择

  1. 选择浅拷贝的场景
    • 当对象成员变量中没有指针类型,或者对象之间可以安全地共享某些资源时,可以选择浅拷贝。这样可以提高性能,减少不必要的内存分配和复制操作。
  2. 选择深拷贝的场景
    • 当对象包含指针类型的成员变量,并且需要确保每个对象都有自己独立的内存空间,避免共享内存带来的问题时,应选择深拷贝。例如,在对象需要被独立修改或销毁,而不影响其他对象的情况下。