enable_from_this 的使用与实现原理说明:
 
shared_from_this()是enable_shared_from_this的成员函数,返回shared_ptr;
注意的是,这个函数仅在shared_ptr的构造函数被调用之后才能使用。
原因是enable_shared_from_this::weak_ptr并不在构造函数中设置,而是在shared_ptr的构造函数中设置。
 
错误的使用代码一:

#include <boost/shared_ptr.hpp>
#include <boost/enable_shared_from_this.hpp> #include <iostream>
using namespace std; class D: public boost::enable_shared_from_this<D>
{
public:
D()
{
cout<<"D::D()"<<endl;
boost::shared_ptr<D> p = shared_from_this();
}
}; int main()
{
boost::shared_ptr<D> a(new D);
return ;
}

程序编译通过,执行结果如下:

D::D()
terminate called after throwing an instance of 'boost::exception_detail::clone_impl<boost::exception_detail::error_info_injector<boost::bad_weak_ptr> >'
  what():  tr1::bad_weak_ptr
Aborted
 
说明在D的构造函数中调用shared_from_this(), 此时D的实例本身尚未构造成功,weak_ptr也就尚未设置,所以程序抛出tr1::bad_weak_ptr异常。
 
 
错误的使用代码二:
 
#include <boost/shared_ptr.hpp>
#include <boost/enable_shared_from_this.hpp> #include <iostream>
using namespace std; class D: public boost::enable_shared_from_this<D>
{
public:
D()
{
cout<<"D::D()"<<endl;
} void func()
{
cout<<"D::func()"<<endl;
boost::shared_ptr<D> p = shared_from_this();
}
}; int main()
{
D d;
d.func();
return ;
}

程序编译通过,执行结果如下:

D::D()
D::func()
terminate called after throwing an instance of 'boost::exception_detail::clone_impl<boost::exception_detail::error_info_injector<boost::bad_weak_ptr> >'
  what():  tr1::bad_weak_ptr
Aborted
 
失败原因分析:
 
在主函数main中,D的实例是在栈上构造,没有使用boost::shared_ptr 的构造方式,
所以boost::enable_shared_from_this中的weak_ptr所指的函数对象也就没有被赋值,
在调用d.func()中使用shared_from_this()函数时
 
----注:shared_from_this的函数实现 ------
    shared_ptr shared_from_this()
    {
        shared_ptr p( weak_this_ );
        BOOST_ASSERT( p.get() == this );
        return p;
    }
----注:shared_from_this的函数实现 ------
 
调用BOOST_ASSERT( p.get() == this );  失败,抛出以上异常。
 
 
最后,我们给出share_from_this()的正确使用例子:
 

#include <boost/shared_ptr.hpp>
#include <boost/enable_shared_from_this.hpp> #include <iostream>
using namespace std; class D: public boost::enable_shared_from_this<D>
{
public:
D()
{
cout<<"D::D()"<<endl;
} void func()
{
cout<<"D::func()"<<endl;
boost::shared_ptr<D> p = shared_from_this();
}
}; int main()
{
boost::shared_ptr<D> p(new D);
p->func();
return ;
}

执行结果:

D::D()
D::func()

(转)enable_from_this方法的使用与陷阱的更多相关文章

  1. 使用Runtime.getRuntime().exec()方法的几个陷阱 (转)

    Process 子类的一个实例,该实例可用来控制进程并获得相关信息.Process 类提供了执行从进程输入.执行输出到进程.等待进程完成.检查进程的退出状态以及销毁(杀掉)进程的方法. 创建进程的方法 ...

  2. [转]使用Runtime.getRuntime().exec()方法的几个陷阱

    Process 子类的一个实例,该实例可用来控制进程并获得相关信息.Process 类提供了执行从进程输入.执行输出到进程.等待进程完成.检查进程的退出状态以及销毁(杀掉)进程的方法. 创建进程的方法 ...

  3. 使用Runtime.getRuntime().exec()方法的几个陷阱

    Process 子类的一个实例,该实例可用来控制进程并获得相关信息.Process 类提供了执行从进程输入.执行输出到进程.等待进程完成.检查进程的退出状态以及销毁(杀掉)进程的方法. 创建进程的方法 ...

  4. 2016-11-02: boost::enable_shared_from_this

    使用场景 当类对象被shared_ptr管理时,需要在类自己定义的函数中把当前对象作为参数传递给其他函数时,必须传递一个shared_ptr,否则就不能保持shared_ptr管理这个类对象的语义.因 ...

  5. CO-类的本质、description方法

    类的本质 1. 类也是个对象 其实类也是一个对象,是Class类型的对象,简称“类对象” Class类型的定义 typedef struct objc_class  *Class; 类名就代表着类对象 ...

  6. OC的特有语法-分类Category、 类的本质、description方法、SEL、NSLog输出增强、点语法、变量作用域、@property @synthesize关键字、Id、OC语言构造方法

    一. 分类-Category 1. 基本用途:Category  分类是OC特有的语言,依赖于类. ➢ 如何在不改变原来类模型的前提下,给类扩充一些方法?有2种方式 ● 继承 ● 分类(Categor ...

  7. 执行Runtime.exec()需要注意的陷阱

    作为Java语言的一部分.java.lang包被隐藏的导入到每一个Java程序.这个包的表面陷阱,经常影响到大多数程序员.这个月,我将讨论运行时exec()方法时的潜伏陷阱. 陷阱4:当运行exec( ...

  8. Java-技术专区-技术栈分析辨证方法

    1.好多公司动不动就JVM.高并发.分布式.微服务等等,我没有实际经验. 2.从事Java开发三年了,目前的职位是高级Java工程师,感觉技术和工资都到了瓶颈,对以后的发展方向有些迷茫. 3.加班时间 ...

  9. JavaScript性能优化

    如今主流浏览器都在比拼JavaScript引擎的执行速度,但最终都会达到一个理论极限,即无限接近编译后程序执行速度. 这种情况下决定程序速度的另一个重要因素就是代码本身. 在这里我们会分门别类的介绍J ...

随机推荐

  1. zabbix4.0LTS安装配置

    一.环境准备 1.最小化安装centos7.5系统 2.安装常用软件包 yum install -y net-tools vim bash-completion 3.关闭selinux和修改主机名 v ...

  2. 《spark机器学习 第二版》 蔡立宇 分享 pdf下载

    链接:https://pan.baidu.com/s/15Y14eAnfj8zf5mXdixbVeQ 提取码:rkdt

  3. netsh常用命令

    netsh常用命令 0.netsh介绍 netsh(Network Shell)是一个windows系统本身提供的功能强大的网络配置命令行工具 1.修改IP地址addr和子网掩码mask netsh ...

  4. LVS 负载均衡 keepalive

    为什么要学lvs 工作在网络模型的7层,可以针对http应用做一些分流的策略,比如针对域名.目录结构, Nginx单凭这点可利用的场合就远多于LVS了.最新版本的Nginx也支持4层TCP负载,曾经这 ...

  5. nohup命令详解

    基础命令学习目录首页 原文链接:https://blog.csdn.net/hfismyangel/article/details/80258126 1.nohup 用途:不挂断地运行命令. 语法:n ...

  6. Oracle purge 用法介绍

    http://blog.csdn.net/indexman/article/details/27379597

  7. 2017年软件工程第十二次作业-PSP总结报告

    回顾1 1.回想一下你曾经对计算机专业的畅想 当初你是如何做出选择计算机专业的决定的?经过一个学期,你的看法改变了么,为什么? 你认为过去接触到的课程是否符合你对计算机专业的期待,为什么?经过一个学期 ...

  8. 王者荣耀交流协会final发布第四次scrum例会

    1.例会照片 成员高远博,冉华,王磊,王玉玲,任思佳,袁玥,王磊,王超同学因参加比赛不在学校,不能出席. master:王玉玲 2.时间跨度 2017年12月4日 18:00 — 18:18,总计18 ...

  9. Notes of Daily Scrum Meeting(11.19)

    Notes of Daily Scrum Meeting(11.19) 现在工程项目进入尾声了,我们的项目中还有一些问题需要解决,调试修改起来进度比较慢,所以昨天就没有贴出项目 进度,今天的团队工作总 ...

  10. b5

    吴晓晖(组长) 过去两天完成了哪些任务 完善推荐算法 展示GitHub当日代码/文档签入记录 接下来的计划 推荐算法 还剩下哪些任务 组员:刘帅珍 过去两天完成了哪些任务: 修改原型,整理背景 明日计 ...