存储 std::weak_ptr<void> 并使用 static_pointer_cast
Storing of std::weak_ptr<void> and using static_pointer_cast
如果将 std::weak_ptr
存储为 static_pointer_cast
,引用计数是否仍然有效?
这是一个非常简单的例子(注意 SmallBox
和 BigBox
class 几乎完全一样):
#define OWNER_SMALLBOX 1
#define OWNER_BIGBOX 2
class Object
{
private:
std::weak_ptr<void> owner;
int ownerType;
public:
void doSomethingIfOwnerStillExist()
{
if(std::shared_ptr<void> ownerShared = owner.lock())
{
switch(ownerType)
{
case OWNER_SMALLBOX:
std::shared_ptr<SmallBox> smallBox = std::static_pointer_cast<SmallBox>(ownerShared);
break;
case OWNER_BIGBOX:
std::shared_ptr<BigBox> bigBox = std::static_pointer_cast<BigBox>(ownerShared);
break;
}//switch
}
}
Object(std::shared_ptr<void> _owner, int _ownerType)
{
owner = _owner;
ownerType = _ownerType;
}
};
class SmallBox
{
private:
std::list< std::shared_ptr<Object> > objects;
public:
static void addObject(std::shared_ptr<SmallBox> _smallBox)
{
std::shared_ptr<void> owner = std::static_pointer_cast<void>(_smallBox);
objects.push_back(std::make_shared<Object>(owner, OWNER_SMALL_BOX));
}
};
class BigBox
{
private:
std::list< std::shared_ptr<Object> > objects;
public:
static void addObject(std::shared_ptr<BigBox> _bigBox)
{
std::shared_ptr<void> owner = std::static_pointer_cast<void>(_bigBox);
objects.push_back(std::make_shared<Object>(owner, OWNER_BIGBOX));
}
};
我知道我可以让 SmallBox
和 BigBox
classes 继承自 GeneralBox
class,并让 void
类型替换为 GeneralBox
类型,但 weak_ptr
也可以指向其他几种类型,这使得继承非常庞大且笨拙。
我很好奇 shared_ptr
是否仍然可以跟踪转换为 void 的弱指针。
如果我对你的问题的理解正确,那么你是在问 std::static_pointer_cast
是否会 return std::shared_ptr
与调用它的参数共享所有权。
答案是肯定的。
addObject
中的 owner
将与 addObject
的函数参数共享所有权,对象中的 owner
将引用相同的控制块,[=16] =] 和 smallBox
, bigBox
在 doSomethingIfOwnerStillExist
.
但是请注意,存储在 objects
中的 shared_ptr
是完全不相关的,因为它们是通过调用 std::make_shared
创建新的 Object
来初始化的将仅由 objects
.
拥有
如果 std::static_pointer_cast
不是与参数共享所有权的实例,那么 std::static_pointer_cast
将毫无用处,因为如果不是,它将不可避免地导致托管指针的双重删除't.
如果将 std::weak_ptr
存储为 static_pointer_cast
,引用计数是否仍然有效?
这是一个非常简单的例子(注意 SmallBox
和 BigBox
class 几乎完全一样):
#define OWNER_SMALLBOX 1
#define OWNER_BIGBOX 2
class Object
{
private:
std::weak_ptr<void> owner;
int ownerType;
public:
void doSomethingIfOwnerStillExist()
{
if(std::shared_ptr<void> ownerShared = owner.lock())
{
switch(ownerType)
{
case OWNER_SMALLBOX:
std::shared_ptr<SmallBox> smallBox = std::static_pointer_cast<SmallBox>(ownerShared);
break;
case OWNER_BIGBOX:
std::shared_ptr<BigBox> bigBox = std::static_pointer_cast<BigBox>(ownerShared);
break;
}//switch
}
}
Object(std::shared_ptr<void> _owner, int _ownerType)
{
owner = _owner;
ownerType = _ownerType;
}
};
class SmallBox
{
private:
std::list< std::shared_ptr<Object> > objects;
public:
static void addObject(std::shared_ptr<SmallBox> _smallBox)
{
std::shared_ptr<void> owner = std::static_pointer_cast<void>(_smallBox);
objects.push_back(std::make_shared<Object>(owner, OWNER_SMALL_BOX));
}
};
class BigBox
{
private:
std::list< std::shared_ptr<Object> > objects;
public:
static void addObject(std::shared_ptr<BigBox> _bigBox)
{
std::shared_ptr<void> owner = std::static_pointer_cast<void>(_bigBox);
objects.push_back(std::make_shared<Object>(owner, OWNER_BIGBOX));
}
};
我知道我可以让 SmallBox
和 BigBox
classes 继承自 GeneralBox
class,并让 void
类型替换为 GeneralBox
类型,但 weak_ptr
也可以指向其他几种类型,这使得继承非常庞大且笨拙。
我很好奇 shared_ptr
是否仍然可以跟踪转换为 void 的弱指针。
如果我对你的问题的理解正确,那么你是在问 std::static_pointer_cast
是否会 return std::shared_ptr
与调用它的参数共享所有权。
答案是肯定的。
addObject
中的 owner
将与 addObject
的函数参数共享所有权,对象中的 owner
将引用相同的控制块,[=16] =] 和 smallBox
, bigBox
在 doSomethingIfOwnerStillExist
.
但是请注意,存储在 objects
中的 shared_ptr
是完全不相关的,因为它们是通过调用 std::make_shared
创建新的 Object
来初始化的将仅由 objects
.
如果 std::static_pointer_cast
不是与参数共享所有权的实例,那么 std::static_pointer_cast
将毫无用处,因为如果不是,它将不可避免地导致托管指针的双重删除't.