2012-10-25 5 views
4

공장에서 포인터를 반환하는 가장 좋은 방법은 무엇입니까? std::unique_ptr 또는 std::shared_ptr 또는 원시 포인터 여야합니까?공장에서 포인터를 반환 중

또한 집계가있는 경우 std::unique_ptr, 포함하는 경우 std::shared_ptr으로 이동해야한다고 들었습니다. 이것이 올바른 방법입니까?

답변

5

아주 특별한 경우에만 원시 포인터를 고려해야합니다 (예 : 포인터를 DLL 경계에 전달하는 경우).

shared_ptrunique_ptr 사이에서, 제 의견은 후자를 선호하는 것입니다. 이렇게하면 인터페이스가 더 유연하게 사용자에게 제공됩니다. 원하는 경우 항상 unique_ptrshared_ptr으로 변환 할 수 있지만 더 중요한 것은 unique_ptr::release을 호출 한 다음 포인터를 수동으로 관리 할 수도 있습니다 (좋은 생각은 아니지만 옵션을 열어두면됩니다).

당신의 공장 반환 unique_ptr에 대한 사용자 정의 Deleter가를 할당 할 필요가있는 경우, unique_ptrshared_ptr 사이에 동작의 차이가 당신이 알고 있어야는 전자가 관리되는 포인터가 nullptr 경우 Deleter가 부르지 만, 후자 없다는 것입니다 의지. 따라서 공장에서 nullptr (실패한 상태 일 수 있음)을 반환 할 수 있고 다른 사람이 unique_ptrshared_ptr으로 변환 한 경우 삭제 기는 nullptr을 인수로 처리 할 수 ​​있는지 확인해야합니다.

+0

내가 아는 한 공장은 해당 오브젝트를 생성하는 데만 책임을집니다. unique_ptr을 사용하면 책임이 공장 고객에게 이전된다는 의미입니까? 어떤 통찰력? DLL 경계의 경우 shared_ptr을 사용하면 사용자 정의 삭제자는 해당 소멸자를 호출 할 수 있습니다. 그렇지 않습니까? – Atul

+0

@Atul 아니요, 'unique_ptr'은 관리 객체가 범위를 벗어날 때 자동으로 삭제합니다. 경계에서 C ABI를 유지해야하는 경우 DLL 경계를 통해 원시 포인터를 전달하는 것은 고려 사항 일뿐입니다. 이것이 문제가되지 않는다면 경계를 넘어서'shared_ptr '을 전달할 수 있습니다. – Praetorian

+0

DLL 경계에서 원시 포인터를 사용해야하는 경우 DLL은 원시 포인터를 반환하는 팩토리 함수와 클라이언트가 개체를 파괴하기 위해 호출해야하는 deleter 함수를 모두 내 보내야합니다. 그런 다음 클라이언트가 포함하는 헤더에 내 보낸 팩토리 함수를 호출하는 래퍼 함수를 ​​정의하고 내 보낸 된 deleter 함수를 호출하는 deleter와 함께'shared_ptr' 또는'unique_ptr'에 저장합니다. – Praetorian

0

확실히 원시 포인터를 반환하면 안됩니다. std :: unique_ptr 및 std :: shared_ptr 대부분의 경우 똑같이 괜찮다고 생각합니다. 물론 표준 스마트 포인터 클래스 만있는 것은 아닙니다. 예를 들어, 간섭 적 참조 카운팅을 구현하는 클래스가 있으며, 사람들은이를 처리하기 위해 특별한 스마트 포인터 클래스 (일반적으로 RefPtr이라고 함)를 구현합니다. CComPtr이있는 COM 인터페이스도 있습니다.

관련 문제