Tôi đang tạo một lớp kiểu chuỗi, chẳng hạn như ví dụ nhỏ dưới đây. Có vẻ như khi xâu chuỗi các hàm thành viên, thì hàm tạo sao chép được gọi. Có cách nào để thoát khỏi cuộc gọi xây dựng bản sao? Trong ví dụ về đồ chơi của tôi dưới đây, rõ ràng là tôi chỉ xử lý tạm thời và do đó "nên" (có thể không theo tiêu chuẩn, nhưng về mặt logic) là một cuộc bầu chọn. Sự lựa chọn tốt thứ hai, để sao chép elision, sẽ là cho hàm tạo di chuyển được gọi, nhưng đây không phải là trường hợp.
class test_class {
private:
int i = 5;
public:
test_class(int i) : i(i) {}
test_class(const test_class& t) {
i = t.i;
std::cout << "Copy constructor"<< std::endl;
}
test_class(test_class&& t) {
i = t.i;
std::cout << "Move constructor"<< std::endl;
}
auto& increment(){
i++;
return *this;
}
};
int main()
{
//test_class a{7};
//does not call copy constructor
auto b = test_class{7};
//calls copy constructor
auto b2 = test_class{7}.increment();
return 0;
}
Chỉnh sửa: Một số làm rõ. 1. Điều này không phụ thuộc vào mức độ tối ưu hóa. 2. Trong mã thực của tôi, tôi có các đối tượng phức tạp (ví dụ như heap được phân bổ) so với ints
auto b = test_class{7};
không gọi hàm tạo sao chép vì nó thực sự tương đương test_class b{7};
và trình biên dịch đủ thông minh để nhận ra trường hợp này và do đó có thể dễ dàng bỏ qua mọi bản sao. Điều tương tự không thể được thực hiện cho b2
.
std::cout
) trong ctor sao chép của mình không? Không có nó, bản sao nên được tối ưu hóa đi.