프로그래밍 이야기

스마트 포인터 노트 auto_ptr, unique_ptr, shared_ptr, weak_ptr

원생계 2023. 9. 25. 16:50

비야네 스트로스트룹

"디자인 패턴 RAII (Resource Acquisition Is Initialization)"

"자원의 획득은 초기화다" == "자원 관리를 스택에 할당한 객체를 통해 수행"

 

C++11 이전

auto_ptr 이 등장. 많은 문제가 있었음.

 

참조 : Why is auto_ptr being deprecated?
https://stackoverflow.com/questions/3697686/why-is-auto-ptr-being-deprecated
"

auto_ptr을 직접적으로 대체할 수 있는(또는 어쨌든 이에 가장 가까운) 것은 unique_ptr입니다. auto_ptr은 할당될 때 소유권을 이전합니다. unique_ptr도 소유권을 이전하는데, codification of move semantics(이동 의미론의 코드화)와 rvalue 참조의 마법 덕분에 훨씬 더 자연스럽게 소유권을 이전할 수 있습니다.(복사를 수행하지 않고 참조를 이동) 또한 나머지 표준 라이브러리와도 훨씬 더 잘 어울립니다(공정하게 말하자면, 나머지 라이브러리가 항상 복사를 필요로 하는 대신 이동 시맨틱을 수용하도록 변경한 덕분입니다).

이름 변경은 (In My Opinion) 환영할 만한 일입니다. auto_ptr은 무엇을 자동화하려는 것인지에 대해 잘 알려주지 않는 반면, unique_ptr은 제공되는 기능에 대해 상당히 합리적인(간결하지만) 설명을 제공합니다.

"

Further information: Here is the official rationale for deprecating auto_ptr

(추가 정보: auto_ptr 사용 중단의 공식적인 근거는 다음과 같습니다.)

https://www.open-std.org/jtc1/sc22/wg21/docs/papers/2005/n1856.html#20.4.5%20-%20Class%20template%20auto_ptr

본문 중 발췌

"

sort(vec.begin(), vec.end(), indirect_less());
Depending upon the implementation of sort, the above line of reasonable looking code may or may not execute as expected, and may even crash! The problem is that some implementations of sort will pick an element out of the sequence, and store a local copy of it.

(sort 구현에 따라 위의 합리적으로 보이는 코드 줄이 예상대로 실행될 수도 있고 실행되지 않을 수도 있으며 심지어 충돌할 수도 있습니다! 문제는 sort의 일부 구현이 시퀀스에서 요소를 선택해 로컬 복사본을 저장한다는 것입니다.)

...

auto_ptr moves from lvalues using copy syntax and is thus fundamentally unsafe.

(auto_ptr은 copy 문법을 사용하여 lvalues에서 이동하므로 근본적으로 안전하지 않습니다.)"

 

auto_ptr은 C++ 11 에서는 deprecated 되었고, C++ 17 에서는 아예 삭제될 예정.

 

추가.

"Jaebum Lee2020-05-06 06:15:23.903
auto_ptr 은 move semantic 이 없었을 시절에 임시방편으로 만들어진 산물입니다. 따라서 소유권이전을 제대로 할 수 없습니다. 뿐만 아니라 이 때문에 컨테이너들의 원소들로도 사용할 수 없구요."

 

C++11 이후

auto_ptr를 unique_ptr가 대체. make_unique로 unique_ptr생성.

 

사용자(프로그래머) 관점.
auto_ptr could be replaced by shared_ptr or unique_ptr depending upon situation
(상황에 따라 auto_ptr을 shared_ptr 또는 unique_ptr로 대체할 수 있습니다.)


Kind of assignments supported by unqiue_ptr
move assignment (1)
assign null pointer (2)
type-cast assignment (3)
copy assignment (deleted!) (4)

Kind of assignments supported by auto_ptr
copy assignment (4) culprit(범인)

MSVC 14.~ 버전의 memory 파일에 선언된 std::unique_ptr 을 보면, 복사 생성자와 복사 대입 연산자가 삭제(= delete)돼있음.
unique_ptr(const unique_ptr&) = delete;
unique_ptr& operator=(const unique_ptr&) = delete;


shared_ptr : using the object AT-DIFFERENT times 참조 카운팅
unique_ptr : access to object is SEQUENTIAL 객체의 유일한 소유권
weak_ptr : shared_ptr 의 순환참조 문제를 방지하기 위한 약한 포인터

 

참조

unique_ptr : https://modoocode.com/229

shared_ptr 와 weak_ptr : https://modoocode.com/252

Rvalue(우측값) 레퍼런스에 관해 : https://modoocode.com/189

rvalue 레퍼런스와 이동 생성자 : https://modoocode.com/227

 

 

 

728x90
반응형