- 主题:这种情况下我该不该把unique_ptr改成shared_ptr?
Class A 持有 Class B
class A {
public:
std::unique_ptr B m_b;
};
Class B持有一个A的回调, 原来是用裸指针
Class B {
public:
A *callback_A;
};
原来一直这么用的,后来看的cpp guidelines,不建议用owning裸指针, 于是乎想把A * 改成weak_ptr, 但是这样的话 就需要把A 改成继承std::enable_shared_from_this, 而且以后还需要把所有 std::unique_ptr<A> 改成std::shared_ptr<A>, 这样改是否合适? 看看大家的意见
--
FROM 117.139.193.*
是的, 严格来说这个不是owning pointer.
某些情况下 A*, 可能存在A* dangling pointer 的问题, 只有weak_ptr不会dangling
比较纠结这一点
【 在 here080 (hero080) 的大作中提到: 】
: 提示:owning裸指针的定义
--
FROM 218.200.160.*
如果不是这种情况呢,A*确实会dangling的时候, 是不是用weak_ptr是最佳实践,还是说, 设置一个set nullptr的接口,主动置空比较好?
【 在 here080 (hero080) 的大作中提到: 】
: 就用裸指针。
: 尤其是如果你这个B里指向的A对象拥有这个B对象,那根本不会有任何风险。
--
FROM 218.200.160.*
是的 A& 也有dangling ref的问题
【 在 here080 (hero080) 的大作中提到: 】
: A&只是一个必须初始化且无法重定向的A*而已
: A&引用的东西跟指针指向的一样,是否失效不是语言本身保证的。
--
FROM 218.200.160.*
感谢详细回答.
确实如你所说. 如果我能100%确认不会失效, 那么用 A& 是最好的. 这样语义明确, 不用到处判空.
但是项目大了之后, 很多人写代码, 我在想要不要 强制一个团队规范, 就是不用在成员变量里面使用 raw pointer, 如果有, 就用weak_ptr来代替. 这样就100%保证了不会出问题, 但是代价是性能会降低.
如果让大家自己判断是否会danging,而使用A&的话, 就有风险. 团队技术人员能力有高有低, 就有隐患
【 在 ziqin (子青|会挽雕弓如满月|西北望|射天狼) 的大作中提到: 】
: 如果要一定保证不失效,就只有使用shared_ptr或者weak_ptr
: 楼主的问题是不是要牺牲效率而从代码级别保证访问callback不会出问题
: 如果callback有可能会在B的生存期内失效,那就不需要讨论,直接上weak_ptr
: ...................
--
FROM 218.200.160.*
你说的是对的.
问题在于一个上百万行的repo里面, 每天很多pr, 可能reviewer没有精力去仔细看每一个地方是否可能danging,出于代码安全性考虑, 我在想要不要全部禁止成员变量持有raw pointer, 虽然不合理, 但是省心. 见我前几条回复有说明
【 在 here080 (hero080) 的大作中提到: 】
: 这个靠的是程序逻辑来控制。
: 你的这个A和B,就是应该使用unique_ptr和裸指针。用shared_ptr和weak_ptr属于典型的滥用。
: 你还没说清楚为什么你这个会有dangling?如果B指向的A拥有这个B,根本就没有dangling的可能啊?
: ...................
--
FROM 218.200.160.*
还有一个问题, 如果A& 失效的话, 有没有类似断言的方法, 可以一步准确定位下来?否则后面各种崩溃, 很难检查W
【 在 ziqin (子青|会挽雕弓如满月|西北望|射天狼) 的大作中提到: 】
: 如果用A&,就根本不存在用shared_ptr还是weak_ptr的问题了吧,言下之意就是callback在B的生存期一直是有效的
--
FROM 218.200.160.*
dangling pointer崩溃不一定崩溃在原地吧?很可能崩溃在一个遥远的地方(内存损坏?)
【 在 here080 (hero080) 的大作中提到: 】
: 崩溃了不就知道发生啥了?
: 你想定位什么?这个不是一处程序问题,是整个一大块程序共同的问题。
--
FROM 218.200.160.*