2011-01-15 3 views
1

누군가가이 필요를 채울 수있는 모든 항목을 돌고 있는지 궁금합니다.존재하지 않습니다 : 하나의 객체가 소유 한 스마트 포인터가 액세스를 허용합니다.

개체 A는 개체 B를 포함합니다. 포인터를 통해 해당 B에 대한 액세스를 클라이언트에 제공하려고합니다 (아마도 0 일 수있는 옵션이 있거나 클라이언트가 복사 가능해야하고 참조를 보유해야 할 수도 있습니다 ...).). 클라이언트는 객체 C를 호출 할 수 있습니다. 일반적으로 완벽한 개발자라면 B에 대한 포인터에 대한 평생의 의미를 위반하지 않도록주의 깊게 작성해야합니다. 그러나 우리는 완벽하지 않습니다. 사실 우리는 완벽하지 않습니다. 꽤 바보 같은 반 시간.

그래서 우리는 오브젝트 C가 "공유"소유권이 아니지만 오브젝트 A가 더 이상 유효하지 않은 상황을 인식 할 정도로 똑똑한 오브젝트 B에 대한 포인터를 갖고 싶습니다. 파괴되었거나 객체 B를 파괴합니다. 더 이상 유효하지 않을 때이 포인터에 액세스하면 어설 션/예외가 발생합니다.

즉, 데이터에 대한 액세스를 안전하고 명확하게 공유하지만 원래의 소유권 의미를 유지하려고합니다. 현재, 객체 중 하나가 소유하고있는 공유 포인터를 찾을 수 없기 때문에 shared_ptr을 대신 사용하고 있습니다. 그러나 나는 명확한 소유권과 공유/약한 포인터가 정말로 그것을 제공하지 않기를 바란다.

이 스마트 포인터를 동적으로 할당 된 메모리 영역에 대한 포인터를 보유하지 않고 멤버 변수에 연결할 수 있다면 더욱 좋습니다.

존재하지 않는다면 나는 그것을 만들려고합니다. 그래서 누군가 먼저 이미 누군가가 그것을 발표했는지 알고 싶습니다.

그리고 BTW, 저는 참고 문헌과 포인터 같은 것들이 이런 종류의 것을 제공한다는 것을 알고 있습니다 ... 저는 더 똑똑한 것을 찾고 있습니다.

+0

글쎄, 아무도 밟아서 하나를 가리키고 있지 않으므로이 시점에서 나는 거기에 없다고 가정하고 있습니다. Loki 라이브러리를 확인해보십시오. 지금까지의 답변은 OK이며 weak_ptr 사용법을 모르는 사람에게 도움이 될 것입니다. 그러나 실제로이 목적을 위해 특별히 설계된 무언가를 찾고 있습니다. 따라서 실제로 받아 들일 수 없습니다. –

답변

1

boost::weak_ptr 당신이 찾고있는 것입니다. 어쩌면 약간의 조작으로 shared_ptr의 생성을 금지하는 것과 같습니다. 또한 동적으로 할당되지 않은 메모리에 대한 포인터를 포함하여 모든 것을 저장할 수 있습니다.

+1

'shared_ptr'의 생성을 허용하지 않는'boost :: weak_ptr'은 꽤 쓸모가 없습니다. 공유 된 포인터를 얻는 다른 방법은'shared_ptr'으로 변환하는 것입니다 (좋은 이유가 있습니다). – jpalecek

+0

weak_ptr에서 shared_ptr을 생성하는 것을 허용하지 않으면 매우 제한된 사용이 될 것 같아서 여러분에게'bad_weak_ptr' 예외를 던져달라고 간청하고 싶습니다. –

+0

weak_ptr은 shared_ptr 시스템의 일부입니다. 나는 사용하고있는 시스템의 의미를 깨뜨리지 않기 위해 노력하고있다. –

0

원하는 의미론은 Qt의 QPointer과 비슷합니다. 이것은 대응하는 QObject이 삭제 될 때 및 nulls 자체를 보유 할 수있는 포인터입니다 (일반적으로 예 : operator delete).

그러나 비슷한 접근 방식에는 고유 한 문제가 있습니다. 즉, 클라이언트가 매달린 포인터를 사용하고 있는지 확인할 수 없기 때문입니다. 예.

QPointer<T> smart_ptr = original_obj; 
T* tmp = smart_ptr; // this might be a function argument etc. 

... // later 
delete original_obj; 

... // even later 
tmp->do_something(); // CRASH 

shared_ptr/ weak_ptr 할 정확히 무엇 인 개체 삭제를 허용하지 않는 일부 "하드"참조를 사용하여 피할 수 있습니다.

BTW, AFAIK, shared_ptr은 멤버 변수를 관리 할 수 ​​있다는 점을 제외하고는 멤버 변수를 가리킬 수 있습니다. 즉, 아무 것도하지 않는 사용자 정의 삭제자를 제공해야합니다.

+0

예, shared_ptr (ptr, null_op) 트릭을 사용했습니다. 시스템의 의미에 위배되지 않는 무언가를 찾고 있습니다. null_op 트릭은 사실 shared_ptr 전체를 완전히 무너 뜨립니다. 어떤 종류의 스마트 포인터도 전혀 가지고 있지 않을 수도 있습니다. –

+0

@Noah Roberts : 모든 것이 분해되지 않는다고 생각합니다. 일부 라이브러리에서 필요로하는 경우 유용 할 수있는'shared_ptr'을 얻었습니다. 하지만 그렇습니다. 이것은'shared_ptr'의 용도가 아닙니다. 선택해야합니다 - 삭제 처리 (회원 변수에 대해서는 항상 적용됨) - 고객은이를 고려해야합니다. 평생의 의미를 위반하지 _ 않습니다. 또는 객체의 수명을 결정하는 참조입니다.이 경우 멤버 변수가 될 수는 없으므로 멤버 변수가 될 수 없습니다. 또는 가비지 컬렉터를 사용하십시오. 다른 방법은 없습니다. – jpalecek

+0

있습니다. 진짜 shared_ptr을 얻지 못하고 있습니다. 물론 shared_ptr과 함께 제공되는 모든 추가 항목을 얻을 수 있습니다. 실제로는 shared_ptr이 완전히 불필요하며 shared_ptr에 수행되는 작업 중 아무 것도 영향을 미치지 않습니다. 이것은 내가 옳은 일을 찾고있는 이유입니다. 어쨌든 고마워. 내 블로그를 언제 작성했는지 계속 확인하십시오 : p –

관련 문제