shared_ptr
을 직접 구현하려고합니다. make_shared
에 문제가 있습니다. std::make_shared
의 주요 기능은 연속 블록 메모리에 카운터 블록과 개체를 할당하는 것입니다. 내가 어떻게 할 수 있니? 나는 개체 및 카운터 블록을 삭제할 때Make_shared - own implementation
template<class T>
class shared_ptr
{
private:
class _ref_cntr
{
private:
long counter;
public:
_ref_cntr() :
counter(1)
{
}
void inc()
{
++counter;
}
void dec()
{
if (counter == 0)
{
throw std::logic_error("already zero");
}
--counter;
}
long use_count() const
{
return counter;
}
};
template<class _T>
struct _object_and_block
{
_T object;
_ref_cntr cntr_block;
template<class ... Args>
_object_and_block(Args && ...args) :
object(args...)
{
}
};
T* _obj_ptr;
_ref_cntr* _ref_counter;
void _check_delete_ptr()
{
if (_obj_ptr == nullptr)
{
return;
}
_ref_counter->dec();
if (_ref_counter->use_count() == 0)
{
_delete_ptr();
}
_obj_ptr = nullptr;
_ref_counter = nullptr;
}
void _delete_ptr()
{
delete _ref_counter;
delete _obj_ptr;
}
template<class _T, class ... Args>
friend shared_ptr<_T> make_shared(Args && ... args);
public:
shared_ptr() :
_obj_ptr(nullptr),
_ref_counter(nullptr)
{
}
template<class _T>
explicit shared_ptr(_T* ptr)
{
_ref_counter = new counter_block();
_obj_ptr = ptr;
}
template<class _T>
shared_ptr(const shared_ptr<_T> & other)
{
*this = other;
}
template<class _T>
shared_ptr<T> & operator=(const shared_ptr<_T> & other)
{
_obj_ptr = other._obj_ptr;
_ref_counter = other._ref_counter;
_ref_counter->inc();
return *this;
}
~shared_ptr()
{
_check_delete_ptr();
}
};
template<class T, class ... Args>
shared_ptr<T> make_shared(Args && ... args)
{
shared_ptr<T> ptr;
auto tmp_object = new shared_ptr<T>::_object_and_block<T>(args...);
ptr._obj_ptr = &tmp_object->object;
ptr._ref_counter = &tmp_object->cntr_block;
return ptr;
}
는하지만, 잘못된 힙 블록 예외가 발생합니다
내가 그런 일을 시도했다.
공유 포인터 관리를 둘러싸고있는 두 가지 필수 코드는 (a) 참조 계산 알고리즘과 (b) 실제 * 삭제 *로이 게시물에 포함시키지 마십시오. 우린 독자가 아니에요. 실제 문제를 보여주는 [** complete MCVE **] (http://stackoverflow.com/help/mcve)를 게시하십시오. "객체와 카운터 블록을 삭제할 때 ..."라는 문장은 절대로 직접적으로 할당되지 않은 두 가지를 삭제할 것을 제안합니다 (사실 'tmp_object'는 전혀 유지되지 않습니다). – WhozCraig
@WhozCraig 고마워요! 게시물을 업데이트했습니다. –
구현에 몇 가지 주요 기능이 없습니다. 코드를 추가하면 기존 코드에서 솔루션이 나타날 수 있습니다. 무엇이 빠졌는가 : deleter를위한 타입 지우기, 관리 객체와 관련없는 포인터를 저장한다. (thread-safe ref 카운팅, weak ref 카운팅, ..)'shared_ptr '은 복잡하다. 현재 양식. – dyp