MST

星途 面试题库

面试题:C++ 中 std::move 如何提升容器性能

假设有一个自定义类 `MyClass`,其中包含一些成员变量(如 `std::string`、`std::vector<int>` 等)。在一个函数中,需要将 `MyClass` 对象放入 `std::vector<MyClass>` 容器中。请说明使用 `std::move` 和不使用 `std::move` 分别对性能有怎样的影响,并编写代码示例展示。
13.7万 热度难度
编程语言C++

知识考点

AI 面试

面试题答案

一键面试
  1. 不使用 std::move 的情况
    • 性能影响:当向 std::vector<MyClass> 容器中添加 MyClass 对象时,如果不使用 std::move,会进行对象的拷贝构造。对于包含 std::stringstd::vector<int> 这样动态分配内存的成员变量的 MyClass 对象,拷贝构造会涉及到内存的重新分配和数据的复制,这在性能上相对开销较大。
    • 代码示例
#include <iostream>
#include <vector>
#include <string>

class MyClass {
public:
    std::string str;
    std::vector<int> vec;

    MyClass(const std::string& s, const std::vector<int>& v) : str(s), vec(v) {}
    // 拷贝构造函数
    MyClass(const MyClass& other) : str(other.str), vec(other.vec) {
        std::cout << "Copy constructor called" << std::endl;
    }
};

void addObjectWithoutMove(std::vector<MyClass>& vec, MyClass obj) {
    vec.push_back(obj);
}

int main() {
    std::vector<MyClass> myVec;
    MyClass obj("Hello", {1, 2, 3});
    addObjectWithoutMove(myVec, obj);
    return 0;
}
  1. 使用 std::move 的情况
    • 性能影响:使用 std::move 时,会调用对象的移动构造函数(如果定义了的话)。移动构造函数通常只是转移资源(如 std::stringstd::vector<int> 内部的指针等),而不是进行数据的复制,大大减少了内存分配和复制操作,提升了性能。
    • 代码示例
#include <iostream>
#include <vector>
#include <string>

class MyClass {
public:
    std::string str;
    std::vector<int> vec;

    MyClass(const std::string& s, const std::vector<int>& v) : str(s), vec(v) {}
    // 拷贝构造函数
    MyClass(const MyClass& other) : str(other.str), vec(other.vec) {
        std::cout << "Copy constructor called" << std::endl;
    }
    // 移动构造函数
    MyClass(MyClass&& other) noexcept : str(std::move(other.str)), vec(std::move(other.vec)) {
        std::cout << "Move constructor called" << std::endl;
    }
};

void addObjectWithMove(std::vector<MyClass>& vec, MyClass obj) {
    vec.push_back(std::move(obj));
}

int main() {
    std::vector<MyClass> myVec;
    MyClass obj("Hello", {1, 2, 3});
    addObjectWithMove(myVec, obj);
    return 0;
}

通过上述代码示例可以看出,使用 std::move 能够减少对象添加到 std::vector 时不必要的数据复制,从而提升性能。特别是在处理包含动态分配资源的对象时,移动语义的优势更为明显。