我指的是Refbase.h,Refbase.cpp和StrongPointer.h
在强指针的Android实现中,任何基于强指针的对象都必须继承refbase,即
sp<TheClass> theObj // TheClass must inherit from class RefBase
这个要求可以在sp
方法之一的代码中看到:
template<typename T> sp<T>& sp<T>::operator =(T* other) {
if (other != NULL) {
other->incStrong(this);
}
if (mPtr != NULL) {
mPtr->decStrong(this);
}
mPtr = other;
return *this;
}
要使incStrong
或decStrong
的来电失败。 。 。 other
和mPtr
必须继承RefBase
问题
为什么sp
已实施,以便其管理的obj 必需成为RefBase
的孩子?甚至没有办法在编译时甚至运行时强制执行此要求。 (好吧if(type()...
)
Std library doesn't have such a requirement
...
经过进一步思考,答案是否能提供灵活性?
如果是,这如何提供灵活性?
答案 0 :(得分:0)
它节省了内存分配。当你写:
std::shared_ptr<Foo> pFoo{new Foo(bar)};
pFoo
实际上有一个指向共享数据结构(在堆上分配)的指针,它具有引用计数器和指向实际Foo对象的指针。通过使对象从RefBase
派生,您可以在对象本身中嵌入引用计数(保存额外的内存分配)。
有趣的是,从C ++ 11开始,您可以通过使用std::make_shared<Foo>
来避免额外的内存分配,RefBase
将执行单个内存分配并在其中构建共享数据结构和Foo对象。
没有编译时间检查m_ptr
的派生是粗心的事实。 RefBase *m_ptr
应该已声明为operator *
,然后T*
(等)应该对sp<T>
执行static_cast。实际上,我可能会将sp_base
继承自T
,其中比较运算符为public,其他函数为protected。
修改强>
再想一想,是相当多的编译时检查。如果incStrong
没有RefBase
成员,则编译将失败,并且几乎肯定不会,除非它来自T*
。我仍然认为将RefBase*
转换为{{1}}本来是更好的检查,但那里的那个可能已经足够了。
答案 1 :(得分:0)
它会自动允许您从实现RefBase的任何对象创建sp,而对于共享指针,您可以在尝试将原始指针包装到共享指针时拍摄自己的脚。
因此,对于shared_ptr,您可能需要这样: http://en.cppreference.com/w/cpp/memory/enable_shared_from_this
对于sp,几乎可以安全地将原始指针传递给sp contructor。