c++编程提倡使用标准库,一个原因是标准库大胆减少对指针的使用。但是许多程序是离不开指针的。包含指针的类需要特别注意复制控制,原因是复制指针时只复制指针中的地址,而不复制指针所指向的对象。这样当把一个对象复制给另一个对象后,当改变一个对象后,另一个对象也会收到牵连。另外一个对象释放掉后,其指针已经被释放掉。而另一个对象还不知道,其实该对象中的指针已经成为悬垂指针。这样再操作就会出现错误。

1. 定义智能指针类

原理:定义一个计数的类,所有复制的都是指向这一个类,每复制一次,该类加1一次;每析构一次,该类减1一次。当次数为0时,释放掉动态申请的空间。

图例:

1)定义一个对象

2)复制一个对象

#include <iostream>
#include <string>
using namespace std; class HasPtr;
//定义计数类
class U_Ptr
{ //没有访问标号,默认为private,保证类的隐私,但是友员类可以随意访问(包括private)
friend class HasPtr;
U_Ptr(int *p) : ip(p), use() {}
~U_Ptr() { cout << "hello" << use << endl; delete ip; }
int *ip;
size_t use; //次数
}; class HasPtr
{
public:
HasPtr(int *p, int v) : ptr(new U_Ptr(p)), val(v) {}
HasPtr(const HasPtr &orig) : ptr(orig.ptr), val(orig.val) { ++ptr->use; }
HasPtr& operator=(const HasPtr &orig);
~HasPtr()
{ cout << "hahha::" << ptr->use << endl; if(--ptr->use == ) delete ptr; }
private:
U_Ptr *ptr;
int val;
}; HasPtr& HasPtr::operator=(const HasPtr &orig)
{
++orig.ptr->use;
if(--ptr->use == )
delete ptr;
ptr = orig.ptr;
val = orig.val;
return *this;
} int main()
{
int i = , j = ;
int *p = new int();
HasPtr hasptr(p, j);
HasPtr hasptr2(hasptr);
}

2. 定义值型类

给指针成员提供语义值。具有值语义的类所定义的对象,其行为很像算术类型的对象:复制值型对象时,会得到一个不同的版本。对副本的改变不会反映在原有对象上。

#include <iostream>
#include <string>
using namespace std; class HasPtr
{
public:
HasPtr(const int &p, int v) : ptr(new int(p)), val(v) {}
HasPtr(const HasPtr &orig) : ptr(new int(*orig.ptr)), val(orig.val) { } //复制值型对象时,会得到一个不同的版本
HasPtr& operator=(const HasPtr &orig);
~HasPtr() { delete ptr; }
private:
int *ptr;
int val;
}; HasPtr& HasPtr::operator=(const HasPtr &orig)
{
*ptr = *orig.ptr; //赋值时,只改变指针指向的值,但是指针是不变的
val = orig.val;
return *this;
} int main()
{
int i = , j = ;
HasPtr hasptr(i, j);
HasPtr hasptr2(hasptr);
hasptr2 = hasptr;
}

【c++】类管理指针成员的更多相关文章

  1. C++ Primer 学习笔记_57_类和数据抽象 --管理指针成员

    复印控制 --管理指针成员 引言: 包括指针的类须要特别注意复制控制.原因是复制指针时.一个带指针成员的指针类 class HasPtr { public: HasPtr(int *p,int i): ...

  2. C++ Primer 有感(管理类的指针成员)

    C++类的指针成员与其他成员有所不同,指针成员指向一个内存地址,该地址的内存需要我没管理. 我现在分析一下为什么要管理指针成员. 有如下Student类,Student.h如下: [cpp] view ...

  3. C++管理指针成员

    1.C++中一般採用以下三种方法之中的一个管理指针成员: (1)指针成员採取常规行为. 这种类具有指针的全部缺陷:具有指针成员且使用默认复制构造函数和赋值操作符,无法避免悬垂指针(两个对象的指针成员指 ...

  4. C++ 带有指针成员的类处理方式

    在一个类中,如果类没有指针成员,一切方便,因为默认合成的析构函数会自动处理所有的内存.但是如果一个类带了指针成员,那么需要我们自己来写一个析构函数来管理内存.在<<c++ primer&g ...

  5. 类1(this指针/const成员函数/类作用域/外部成员函数/返回this对象的函数)

    假设我们要设计一个包含以下操作的 Sales_data 类: 1.一个 isbn 成员函数,用于返回对象的 book_no 成员变量 2.一个 combine 成员函数,用于将一个 Sales_dat ...

  6. YTU 2636: B3 指向基类的指针访问派生类的成员函数

    2636: B3 指向基类的指针访问派生类的成员函数 时间限制: 1 Sec  内存限制: 128 MB 提交: 433  解决: 141 题目描述 领导类(Leader)和工程师类(Engineer ...

  7. 15.含有指针成员的类的拷贝[ClassCopyConstructorWithPointerMember]

    [题目] 下面是一个数组类的声明与实现.请分析这个类有什么问题,并针对存在的问题提出几种解决方案.  C++ Code  123456789101112131415161718192021222324 ...

  8. (转)MFC中获得各个类的指针/句柄 ID的总结

    http://www.cnblogs.com/ylhome/archive/2009/10/06/1578478.html 一般我们使用的框架是VC提供的Wizard生成的MFC App Wizard ...

  9. MFC中获取App,MainFrame,Doc和View类等指针的方法

    From: http://hi.baidu.com/wxnxs/item/156a68f5b3b4ed18e3e3bd03   MFC中获取App,MainFrame,Doc和View类等指针的方法 ...

随机推荐

  1. shiro中移除jsessionid的解决方案

    在web.xml配置文件中设置 <session-config> <!-- Disables URL-based sessions (no more 'jsessionid' in ...

  2. MIPS rev.1 指令参数

    由于MIPS各个版本之间的操作数会变,如果出现无法识别的情况 需要根据官方的MIPS instruction手册逐条核对,此处的版本为Rev.1 //******MIPS-55*********// ...

  3. Unity3D 之PC客户端的分辨率自定义

    在Player Setting中可以自定义分辨率,但在PC版本中如果使用Display Resolution Dialog选项,会发现在分辨率选项中只有预定义的那些,而并没有在Player Setti ...

  4. robotframework+jenkins分布式执行自动化测试用例

    http://blog.sina.com.cn/s/blog_53f023270101sc3w.html http://www.cnblogs.com/2test/p/5336842.html

  5. 群晖Synology

    简介 群晖是做的最好的一家NAS公司,声称是买软件卖硬件,软件有丰富的功能. 白群晖就是指从正规渠道买软件+硬件,价格昂贵,性价比低. 黑群晖是指自己搭建或购买单独的硬件(可以是电脑主机.可以是其他厂 ...

  6. C# 读Autofac源码笔记(2)

    刚看了下Autofac属性注入的源码 首先看看WithProperty方法   image.png Autofac将我们的属性值,存在了一个list集合中   image.png 然后将这个集合传递到 ...

  7. eclipse 创建maven

    下载地址自行搜索关键字:“eclipse官网”即可,注意下版本,32bit or 64bit. maven插件以及svn等相关插件安装设置问题不在这里赘述,有时间的话会发布出来. 在这里说一下,第一. ...

  8. sun.misc.Unsafe.park(Native Method)

    关闭tomcat时或者重启tomcat时 log4j2 报错: sun.misc.Unsafe.park(Native Method) 异常信息: 30-Aug-2018 15:59:34.900 S ...

  9. Oracle 字符集常见字符集及解决方案

    Oracle 字符集常见字符集及解决方案 优先级别:alter session>环境变量>注册表>参数文件 一.查看字符集: 1.查询服务端字符集: select userenv(' ...

  10. vector在一个循环里同时删除插入

    vector<int> a; a.push_back(10); a.push_back(20); a.push_back(30); a.push_back(40); a.push_back ...