boost::shared_ptr
boost::shared_ptr是boost库中用来管理指针的模板,使用它需要#include <boost/shared_ptr.hpp>。本文介绍它的一些基本用法。
第一,boost::shared_ptr管理的指针所指向的对象必须在堆中,因为该模板会在对象离开作用域后调用delete方法,如果对象位于栈中,程序编译能通过,但在运行中会崩溃。另外改模板提供了swap方法,可以让两个模板指针相互交换所指向的对象。
#include <vector>
#include <set>
#include <iostream>
#include <algorithm>
#include <boost/shared_ptr.hpp> // The application will produce a series of
// objects of type Foo which later must be
// accessed both by occurrence (std::vector)
// and by ordering relationship (std::set). struct Foo
{
Foo( int _x ) : x(_x) {}
~Foo() { std::cout << "Destructing a Foo with x=" << x << "\n"; }
int x;
/* ... */
}; typedef boost::shared_ptr<Foo> FooPtr; typedef struct FooPtrOps
{
bool operator()( const FooPtr & a, const FooPtr & b )
{ return a->x > b->x; }
void operator()( const FooPtr & a )
{ std::cout << a->x << "\n"; }
} foo_ptr_ops; foo_ptr_ops ins_foo_ptr_ops1 = foo_ptr_ops();
FooPtrOps *ins_foo_ptr_ops2 = new FooPtrOps();
FooPtrOps *ins_foo_ptr_ops3 = new foo_ptr_ops; int main()
{
{
std::vector<FooPtr> foo_vector;
std::set<FooPtr,FooPtrOps> foo_set; // NOT multiset! FooPtr foo_ptr( new Foo( ) );
foo_vector.push_back( foo_ptr );
foo_set.insert( foo_ptr ); foo_ptr.reset( new Foo( ) );
foo_vector.push_back( foo_ptr );
foo_set.insert( foo_ptr ); foo_ptr.reset( new Foo( ) );
foo_vector.push_back( foo_ptr );
foo_set.insert( foo_ptr ); foo_ptr.reset ( new Foo( ) );
foo_vector.push_back( foo_ptr );
foo_set.insert( foo_ptr ); std::cout << "foo_vector:\n";
std::for_each( foo_vector.begin(), foo_vector.end(), ins_foo_ptr_ops1 ); std::cout << "\nfoo_set:\n";
std::for_each( foo_set.begin(), foo_set.end(), *ins_foo_ptr_ops3 ); FooPtr foo_ptr1( new Foo( ) );
FooPtr foo_ptr2( new Foo( ) );
std::cout << "foo_ptr1: " << foo_ptr1->x << '\n';
std::cout << "foo_ptr2: " << foo_ptr2->x << '\n'; foo_ptr1.swap(foo_ptr2);
std::cout << "After swap:\n";
std::cout << "foo_ptr1: " << foo_ptr1->x << '\n';
std::cout << "foo_ptr2: " << foo_ptr2->x << '\n'; foo_ptr2.swap(foo_ptr1);
std::cout << "Swap again:\n";
std::cout << "foo_ptr1: " << foo_ptr1->x << '\n';
std::cout << "foo_ptr2: " << foo_ptr2->x << '\n'; int a = ;
int b[] = {, , , };
int *c = new int();
int *d = new int[]; /*
* Because variable a and b are on stack, while boost::shared_ptr will call delete method,
* the following two rows of code will cause error.
*/
// boost::shared_ptr<int> bsa(&a); // Error: Signal: SIGABRT (Aborted)
// boost::shared_ptr<int> bsb(b); // Error: Signal: SIGABRT (Aborted)
boost::shared_ptr<int> bsc(c);
boost::shared_ptr<int> bsd(d);
std::cout << "bsc: " << *bsc << " bsd: " << *bsd << std::endl; std::cout << "The variable field finished." << "\n";
} int *c = new int();
int *d = new int[];
boost::shared_ptr<int> bsc(c);
boost::shared_ptr<int> bsd(d);
std::cout << "bsc: " << *bsc << " bsd: " << *bsd << std::endl; std::cout << "\nProgram done.\n";
}
程序的运行结果:
foo_vector: foo_set: foo_ptr1:
foo_ptr2:
After swap:
foo_ptr1:
foo_ptr2:
Swap again:
foo_ptr1:
foo_ptr2:
bsc: bsd:
The variable field finished.
Destructing a Foo with x=
Destructing a Foo with x=
Destructing a Foo with x=
Destructing a Foo with x=
Destructing a Foo with x=
Destructing a Foo with x=
bsc: bsd: Program done.
第二,boost::shared_ptr支持隐藏类的定义。如下面的代码中,class implementation的定义可以放置于另一个源文件中,在利用boost::shared_ptr管理implementation类型的指针变量时,可以先声明一下类implementation,然后就能定义boost::shared_ptr< implementation >类型的指针变量。
#include <boost/shared_ptr.hpp>
#include <iostream>
#include <algorithm> void print_val(int v)
{
std::cout << v << " ";
} class example
{
public:
example();
void do_something();
int val[];
class implementation;
boost::shared_ptr< implementation > _imp; // hide implementation details
}; class example::implementation
{
public:
~implementation() { std::cout << "destroying implementation\n"; }
}; example::example() : _imp( new implementation ) {} void example::do_something()
{
std::cout << "use_count() is " << _imp.use_count() << " ";
std::for_each(val, val + , print_val);
std::cout << "\n";
} int main()
{
example a;
a.val[] = ;
a.val[] = ;
a.val[] = ;
a.do_something();
example b(a);
b.do_something();
example c;
c = a;
a.do_something();
b.do_something();
c.do_something();
return ;
}
程序的运行结果:
use_count() is
use_count() is
destroying implementation
use_count() is
use_count() is
use_count() is
destroying implementation
第三,使用boost::shared_ptr提供的reset()方法,可以使boost::shared_ptr管理的指针所指向的对象的引用计数减一。当所指对象的引用计数减至0时,所指对象的析构函数将被调用,所指对象被销毁。
#include <iostream>
#include <string>
#include <boost/shared_ptr.hpp> using namespace std; class Book
{
private:
string name_; public:
Book(string name) : name_(name)
{
cout << "Creating book " << name_ << " ..." << endl;
} ~Book()
{
cout << "Destroying book " << name_ << " ..." << endl;
}
}; int main()
{
cout << "=====Main Begin=====" << endl;
{
boost::shared_ptr<Book> myBook1(new Book("「1984」"));
cout << "myBook1: " << myBook1.use_count() << endl;
boost::shared_ptr<Book> myBook2(myBook1);
cout << "myBook1: " << myBook1.use_count() << endl;
boost::shared_ptr<Book> myBook3;
myBook3 = myBook1; cout << "\n****************************\n";
cout << "myBook1: " << myBook1.use_count() << endl;
cout << "myBook2: " << myBook2.use_count() << endl;
cout << "myBook3: " << myBook3.use_count() << endl; cout << "\n****************************\n";
myBook1.reset();
cout << "myBook1: " << myBook1.use_count() << endl;
cout << "myBook2: " << myBook2.use_count() << endl;
cout << "myBook3: " << myBook3.use_count() << endl; cout << "\n****************************\n";
myBook3.reset();
cout << "myBook1: " << myBook1.use_count() << endl;
cout << "myBook2: " << myBook2.use_count() << endl;
cout << "myBook3: " << myBook3.use_count() << endl; cout << "\n****************************\n";
myBook2.reset();
cout << "myBook1: " << myBook1.use_count() << endl;
cout << "myBook2: " << myBook2.use_count() << endl;
cout << "myBook3: " << myBook3.use_count() << endl; cout << "After reset ..." << endl;
}
cout << "===== Main End =====" << endl; return ;
}
程序的运行结果:
=====Main Begin=====
Creating book 「」 ...
myBook1:
myBook1: ****************************
myBook1:
myBook2:
myBook3: ****************************
myBook1:
myBook2:
myBook3: ****************************
myBook1:
myBook2:
myBook3: ****************************
Destroying book 「」 ...
myBook1:
myBook2:
myBook3:
After reset ...
===== Main End =====
boost::shared_ptr的更多相关文章
- [5] 智能指针boost::shared_ptr
[1]boost::shared_ptr简介 boost::shared_ptr属于boost库,定义在namespace boost中,包含头文件#include<boost/shared_p ...
- 记录以下boost::shared_ptr的一个使用细节
shared_ptr<T>::operator->返回的是T*类型指针,非const T*指针.因此通过const shared_ptr<T>&类型的ptr可以直 ...
- 关于智能指针boost::shared_ptr
boost库中的智能指针shared_ptr, 功能强大, 且开销小,故受到广大coder的欢迎. 但在实际的使用过程中,笔者也发现了一些不足. 1.定制的删除器 shared_ptr除了可以使用默认 ...
- #include <boost/shared_ptr.hpp>
共享指针 这个智能指针命名为boost::shared_ptr,定义在boost/shared_ptr.hpp里.智能指针boost::shared_ptr基本上类似于boost::scoped_pt ...
- 智能指针剖析(下)boost::shared_ptr&其他
1. boost::shared_ptr 前面我已经讲解了两个比较简单的智能指针,它们都有各自的优缺点.由于 boost::scoped_ptr 独享所有权,当我们真真需要复制智能指针时,需求便满足不 ...
- C++智能指针剖析(下)boost::shared_ptr&其他
1. boost::shared_ptr 前面我已经讲解了两个比较简单的智能指针,它们都有各自的优缺点.由于 boost::scoped_ptr 独享所有权,当我们真真需要复制智能指针时,需求便满足不 ...
- 【C++】boost::shared_ptr boost::make_shared
一.shared_ptr shared_ptr作为一个动态分配的对象,当最后一个指向其内容的指针销毁(destroyed)或重置(reset),其指向的内容会被销毁(deleted).不再需要显式调用 ...
- 智能指针tr1::shared_ptr、boost::shared_ptr使用
对于tr1::shared_ptr在安装vs同一时候会自带安装,可是版本号较低的不存在.而boost作为tr1的实现品,包括 "Algorithms Broken Compiler Work ...
- boost shared_ptr weak_ptr
文档: http://www.boost.org/doc/libs/1_57_0/libs/smart_ptr/shared_ptr.htm shared_ptr构造有个原型 template< ...
随机推荐
- JavaScript中相等==和严格相等===的区别
在JavaScipt中==(相等)和===(严格相等,strick equality 也有译作“恒等”.“全等”)用于比较两个值是否相等,两个运算符允许任意类型的操作数.如果操作数相等则返回true, ...
- 【转】深入理解Java多态原理
之前一直知道多态是什么东西,平时敲代码也经常用到多态,但一直没有真正了解多态底层的运行机制到底是怎么样的,这两天才研究明白点,特地写下来,跟各位同学一起进步,同时也希望各位大神指导和指正. 多态的概念 ...
- “浪潮杯”第九届山东省ACM大学生程序设计竞赛重现赛 C-Cities
题目描述:There are n cities in Byteland, and the ith city has a value ai. The cost of building a bidirec ...
- Linq学习(二)-本次学习用到的资料
本次学习用到的数据库初始化脚本如下 use KMS create table Blog_User ( UserId ,1), NickName ), CreateTime datetime ) cre ...
- Linux查找目录下的按时间过滤的文件
在维护项目中,有时会指定都一些条件进行过滤文件,并对该批文件进行操作:这时我们将使用shell命令进行操作:直接上代码 #!/bin/sh #BEGIN #`find ./ ! -name " ...
- CF414B Mashmokh and ACM
思路: dp. 实现: 1.O(n5/2) #include <iostream> #include <cstdio> using namespace std; ; ][]; ...
- python框架之Flask基础篇(一)
一.第一个hello world程序 # coding=utf-8 from flask import Flask app = Flask(__name__) @app.route('/') def ...
- Android的HttpUrlConnection类的GET和POST请求
/** * get方法使用 */ private void httpGet() { new Thread() { @Override public void run() { //此处的LOGIN是请求 ...
- React Native导航器Navigator
React Native导航器Navigator 使用导航器可以让你在应用的不同场景(页面)间进行切换.导航器通过路由对象来分辨不同的场景.利用renderScene方法,导航栏可以根据指定的路由来渲 ...
- html5——:hover事件触发自己的:afert伪元素事件
:hover事件触发自己的:afert伪元素事件中间是没有空格的