zoukankan      html  css  js  c++  java
  • c++ shared_ptr储存this指针多次析构问题之enable_shared_from_this解决方案

    #include <iostream>
    #include <memory>
    #include <cassert>
    /*
    		//this //调用了两次析构函数,
    		ParentPtr p(this);
    		//智能指针出了作用域后就delete this ,析构了
    		//所以错了,为了解决这个问题,就需要自身的类继承于 std::enable_shared_from_this<Type>
    		//将ParentPtr p(this) 换成, shared_from_this();
     
     */
    class Parent;
    typedef std::shared_ptr<Parent> ParentPtr;
    typedef std::weak_ptr<Parent> WeakParentPtr;
    
    class Child : public std::enable_shared_from_this<Child> {
    	public:
    		WeakParentPtr father;
    //		ParentPtr father;
    		~Child();
    		Child();
    		void checkRelation();
    };
    
    typedef std::shared_ptr<Child> ChildPtr;
    typedef std::weak_ptr<Child> WeakChildPtr;
    
    class Parent : public std::enable_shared_from_this<Parent> {
    	public:
    		WeakChildPtr son;
    //		ChildPtr son;
    		~Parent();
    		Parent();
    		void checkRelation();
    };
    
    void handleChildAndParentRef(const Parent &p, const Child &c) {
    	if(c.father.lock().get() == &p && p.son.lock().get() == &c) {
    		std::cout << "right relation" << std::endl;	
    	}else {
    		std::cout << "oop!!!!!!" << std::endl;
    	}
    }
    void handleChildAndParent(const ParentPtr &p, const ChildPtr &c) {
    	assert(c);
    	assert(p);
    	if(c->father.lock() == p && p->son.lock() == c) {
    		std::cout << "right relation" << std::endl;	
    	}else {
    		std::cout << "oop!!!!!!" << std::endl;
    	}
    }
    Child::Child() { std::cout << "hello child" << std::endl; }
    Child::~Child() { std::cout << "bye child" << std::endl; }
    Parent::Parent() { std::cout << "hello parent" << std::endl; }
    Parent::~Parent() { std::cout << "bye parent" << std::endl; }
    
    void Parent::checkRelation() {
    	auto ps = son.lock();
    	if(ps) {
    		//this //调用了两次析构函数,
    //		ParentPtr p(this);
    		//handleChildAndParent(p, ps);	
    
    		//智能指针出了作用域后就delete this ,析构了
    		//所以错了,为了解决这个问题,就需要自身的类继承于 std::enable_shared_from_this<Type>
    		//将ParentPtr p(this) 这种错误形式换成, shared_from_this()
    		handleChildAndParent(shared_from_this(), ps);	
    	}
    		std::cout << "after call checkRelation" << std::endl;
    }
    
    void Child::checkRelation() {
    	
    }
    void testParentAndChild() {
    	//若Parent 继承于 std::enable_shared_from_this<Type>
    	//则 Parent pp; 这种静态的就不推荐
    	ParentPtr p(new Parent());
    	ChildPtr c(new Child());
    	p->son = c;
    	c->father = p;
    	p->checkRelation();
    }
    
    static void interfaceOfSharedPtr();
    static void sharedPtrWithWeakPtr();
    static void uniquePtr();
    
    int main(void) {
    	testParentAndChild();	
    	return 0 ;
    }
    
    
  • 相关阅读:
    Delphi中TFlowPanel实现滚动条效果
    Delphi组件开发-在窗体标题栏添加按钮(使用MakeObjectInstance(NewWndProc),并处理好多消息)
    减小Delphi的Exe文件大小(11种方法)
    画出太极图
    类似地图的以鼠标为中心缩放图像
    andoid x项目的优化 1
    ICON图标文件解析
    所有语言的Awesome(2)
    获取EIP(汇编语言直接给Delphi变量赋值)
    Qt Windows下链接子系统与入口函数(终结版)(可同时存在main和WinMain函数)
  • 原文地址:https://www.cnblogs.com/lyxf/p/12358294.html
Copyright © 2011-2022 走看看