在网上简单百度了下这个错误,发现大多数说的是下面两种情况

情况1 没有用shared来管理的类

class A:public enable_shared_from_this
{};
int main()
{
	A a;
	auto p = a.shared_from_this();
}

情况2 在构造函数调用shared_from_this

class A:public enable_shared_from_this
{
	A()
	{
		auto p = shared_from_this();
	}
}

然而我的问题不是这两种情况。最后调试了好久终于弄明白问题在哪了,这个过程中也对shared_ptr和enable_shared_from_this的源码看懂了七七八八,对enable_shared_from_this也算是理解了。

所谓的shared_ptr,其实就是在指针和对象之间加了一层。指针要实现计数,总得有个地方保存数字吧。这个地方得让所有指向同一个对象的智能指针都能访问到,那只能是堆了。也就是说,只能指针内部有个指针,指向堆中,那个地方就是放引用计数的地方。这个地方的地址就是关键。enable_shared_form_this要解决的,就是类自己怎么知道那个放引用计数的地方在哪?通过继承enable_shared_form_this,其实继承了一个名字为_M_weak_this的weak_ptr指针。这个指针就是要指向对象自己的指针,当需要shared_from_this的时候,返回的就是用这个weakptr初始化构造成的sharedptr。

我最开始看源代码很奇怪没找到哪里有初始化这个weakptr的地方啊。enable_shared_from_this的源代码很少,如下

 template<typename _Tp>
    class enable_shared_from_this
    {
    protected:
      constexpr enable_shared_from_this() noexcept { }

      enable_shared_from_this(const enable_shared_from_this&) noexcept { }

      enable_shared_from_this&
      operator=(const enable_shared_from_this&) noexcept
      { return *this; }

      ~enable_shared_from_this() { }

    public:
      shared_ptr<_Tp>
      shared_from_this()
      { return shared_ptr<_Tp>(this->_M_weak_this); }

      shared_ptr<const _Tp>
      shared_from_this() const
      { return shared_ptr<const _Tp>(this->_M_weak_this); }

#if __cplusplus > 201402L || !defined(__STRICT_ANSI__) // c++1z or gnu++11
#define __cpp_lib_enable_shared_from_this 201603
      weak_ptr<_Tp>
      weak_from_this() noexcept
      { return this->_M_weak_this; }

      weak_ptr<const _Tp>
      weak_from_this() const noexcept
      { return this->_M_weak_this; }
#endif

    private:
      template<typename _Tp1>
	void
	_M_weak_assign(_Tp1* __p, const __shared_count<>& __n) const noexcept
	{ _M_weak_this._M_assign(__p, __n); }

      // Found by ADL when this is an associated class.
      friend const enable_shared_from_this*
      __enable_shared_from_this_base(const __shared_count<>&,
				     const enable_shared_from_this* __p)
      { return __p; }

      template<typename, _Lock_policy>
	friend class __shared_ptr;

      mutable weak_ptr<_Tp>  _M_weak_this;
    };

后来看了一些文章才明白,这个初始化是在shareptr的构造函数中完成的。在sharedptr的构造函数中,会检测要构造的对象是否继承了enable_shared_from_this.如果继承了这个类,就会对这个类中的_M_weak_this赋值,让这个weakptr中记录下来sharedptr保存引用计数的地方的内存地址。从而实现了功能。

这里是怎么判断对象有没有继承enable_shared_from_this呢?

      template<typename _Yp, typename _Yp2 = typename remove_cv<_Yp>::type>
	typename enable_if<__has_esft_base<_Yp2>::value>::type
	_M_enable_shared_from_this_with(_Yp* __p) noexcept
	{
	  if (auto __base = __enable_shared_from_this_base(_M_refcount, __p))
	    __base->_M_weak_assign(const_cast<_Yp2*>(__p), _M_refcount);
	}

      template<typename _Yp, typename _Yp2 = typename remove_cv<_Yp>::type>
	typename enable_if<!__has_esft_base<_Yp2>::value>::type
	_M_enable_shared_from_this_with(_Yp*) noexcept
	{ }

如上的两个函数,分别是给继承了enable_shared_from_this和没继承enable_shared_from_this用的。可以看到是用模板的方法,在编译期实现的。不过具体这个__has_esft_base是怎么做到的,我没太看懂。模板真的是黑魔法。

我遇到的问题就是在这一步,应该执行上一个函数,结果执行的却是下面的函数。这说明我没有正确继承enable_shared_from_this啊!我翻回去一看,原来是因为我没有公有继承。c++默认不写的话就是私有继承。终于找到问题所在了。

1 对 “调试bad_weak_ptr报错”的想法;

  1. Thhe pleaasure rooims musicFree sex e-mail cardsCockk ring prostrateHoww does
    a vaghina lubricateBooat cver codk piit coverSteaming pornn gynecoHoow bigg arre sizse c breastsSwinmger clubs daytonn ohioBodybuilring nure femalePale breastsSarah siulverman gayy militaryVintage racng illustrationsSeex girls inn srilankaNudde twiin lesbnians polrn tubeNiip and tuck nide picsHow doo yoou do anl sexCum femalee suckinmg tgpsYounmg giel cock
    suckingEmory offender proram sexdual universityNuude picturre
    of mickey mantleWmon nudeWemen aand bbig cockCastro supreme bottoms foor tigerr tysonControl facil curves maya clampRednwck fuckiong
    milfMarue mccray porn actressLoooking hoot iin bikiniRuxsian mature partyShemale biig ock sexVery younmg spanish
    teensDick tugersCuppijng hajd penisLarge porn move filesClicfk annd view pornFrree gayy teenn bboy
    pornSexy grraphic novels

    Stoop bby mmy web pasge – sis teaches stepbro how to fuck

发表回复

您的邮箱地址不会被公开。 必填项已用 * 标注