2012-02-22 36 views
9
std::unique_ptr<int> ptr; 
ptr = new int[3];    // error 
 
error C2679: binary '=' : no operator found which takes a right-hand operand of type 'int *' (or there is no acceptable conversion) 

Tại sao lại không được biên dịch? Làm thế nào tôi có thể đính kèm con trỏ bản địa vào cá thể unique_ptr hiện tại?unique_ptr operator =

Trả lời

27

Thứ nhất, nếu bạn cần một mảng độc đáo, làm cho nó

std::unique_ptr<int[]> ptr; 
//    ^^^^^ 

này cho phép con trỏ thông minh để sử dụng một cách chính xác delete[] deallocate con trỏ, và xác định operator[] để bắt chước một mảng bình thường.


Sau đó, operator= chỉ định để tham khảo rvalue của con trỏ độc đáo và con trỏ không thô, và một con trỏ liệu không thể được ngầm chuyển đổi sang một con trỏ thông minh, để tránh phân công ngẫu nhiên mà phá vỡ độc đáo. Do đó, một con trỏ thô không thể được gán trực tiếp cho nó. Cách tiếp cận chính xác được đưa nó vào constructor:

std::unique_ptr<int[]> ptr (new int[3]); 
//       ^^^^^^^^^^^^ 

hoặc sử dụng .reset chức năng:

ptr.reset(new int[3]); 
// ^^^^^^^  ^

hoặc dứt khoát chuyển con trỏ liệu đến một con trỏ duy nhất:

ptr = std::unique_ptr<int[]>(new int[3]); 
// ^^^^^^^^^^^^^^^^^^^^^^^  ^

Nếu bạn có thể sử dụng C++ 14, thích sử dụng make_unique function hơn bằng cách sử dụng new ở tất cả:

ptr = std::make_unique<int[]>(3); 
// ^^^^^^^^^^^^^^^^^^^^^^^^^^ 
+2

Lý do là 'operator =' không chấp nhận 'int *' * và * hàm tạo dùng 'int *' được đánh dấu 'tường minh' (cho cả hai' std :: unique_ptr 'và' std :: unique_ptr '). 'operator =' là toán tử gán nhiệm vụ và không phải là toán tử gán bản sao không có gì để làm với nó. –

+0

@LucDanton: Đúng vậy. Đã cập nhật để bao gồm điều đó. – kennytm

2

Thêm vào câu trả lời từ KennyTM

(từ C++ 11)

tr = (decltype(tr)(new int[3])); 

Cá nhân tôi thích điều này vì nó làm cho việc cập nhật các loại tr dễ dàng hơn. (Chỉ có một nơi để cập nhật)