智能指针

智能指针

人盡茶涼 提交于 2020-01-26 22:31:48
内存泄露(臭名昭著的BUG) 动态申请堆空间,用完后不归还 C++语言中没有垃圾回收机制 指针无法控制所指堆空间的生命周期 我们需要什么? 需要一个特殊的指针 指针生命周期结束时主动释放堆空间 一片堆空间最多只能由一个指针标识 杜绝指针运算和指针比较(可以避免野指针) 解决方法 指针操作符(->和*) 只能通过类的成员函数重载 重载函数不能使用参数 只能定义一个重载函数 小结: 指针操作符(->和*)可以被重载 重载操作符能够使用对象代替指针 智能指针只能用于指向堆空间的内存 智能指针的意义在于最大程度的避免内存问题 智能指针使用军规:只能用来指向堆空间中的对象或者变量 #include <iostream> #include <string> using namespace std; class Test { int i; public: Test(int _val) { this->i = _val; cout << "Test(int _val)" << endl; } ~Test() { cout << "~Test()" << endl; } int get_value() { return i; } }; class Pointer { Test* mp; public: Pointer(Test *p = NULL) { mp = p; } //执行深拷贝

C++智能指针详解1——概述

做~自己de王妃 提交于 2020-01-22 21:37:14
问题 从C开始, 指针就很重要,但却是麻烦的根源 ——要确保它们的生存期与它们所引用的对象的生存期相匹配,特别是当多个指针引用同一个对象时。 解决方法 避免此类问题的常用方法是使用“智能指针” 。智能指针可以“知道”它是否是指向对象的最后一个指针,并且仅当该指针作为对象的“最后所有者”被销毁时,才删除关联的对象。 分类 从C++ 11开始,C++标准库提供了 两种类型的智能指针 : shared_ptr :实现共享所有权——多个智能指针可以引用同一个对象,以便只有销毁对它的最后一个引用时才释放该对象及其相关资源。为了在更复杂的场景中执行此任务,提供了辅助程序类,例如weak_ptr,bad_weak_ptr和enable_shared_from_this。 unique_ptr :实现独占所有权——确保一个对象一次只能被一个智能指针引用,但可以转让所有权。 该指针对于避免资源泄漏(例如,在使用new创建对象并在发生异常时或之后丢失的delete调用)特别有用。 C++ 98标准库提供一个智能指针auto_ptr,该类专门用于执行unique_ptr现在提供的任务。在TR1中引入了shared_ptr并且在C ++11中引入了unique_ptr之后, C ++ 11正式弃用了auto_ptr 。 头文件 所有智能指针类均在<memory>头文件中定义。 来源: CSDN 作者:

C++ 智能指针详解

生来就可爱ヽ(ⅴ<●) 提交于 2020-01-18 22:44:49
C++ 智能指针详解 文章目录 C++ 智能指针详解 1. 智能指针能解决什么问题? 2. 智能指针的发展 3. 智能指针 shared_ptr 3.1 创建shared_ptr实例 3.2 访问所指对象 3.3 拷贝和赋值操作 3.4 检查引用计数 3.5 reset 函数 4. 智能指针 weak_ptr 4.1 weak_ptr 的基本用法 4.2 weak_ptr 的相关函数 4.3 weak_ptr 总结 5. 智能指针 unique_ptr 6. 智能指针注意事项 1. 智能指针能解决什么问题? 在C++中,动态内存的管理是通过一对运算符来完成的: new ,在动态内存中为对象分配空间并返回一个指向该对象的指针,可以选择对对象进行初始化; delete ,接受一个动态对象的指针,销毁该对象,并释放与之关联的内存。 动态内存的使用很容易出问题,因为确保在正确的时间释放内存是极其困难的。有时会忘记释放内存,在这种情况下会产生 内存泄露 ;有时在尚有指针引用内存的情况下就释放了它,在这种情况下就会产生引用非法内存的指针。 为了更容易(同时也更安全)地使用动态内存,C++11标准库提供智能指针(smart pointer)类型来管理动态对象。 智能指针的行为类似常规指针,重要的区别是它负责 自动释放所指的对象 。 智能指针是模板类而不是指针 。类似vector

c++使用智能指针需要注意的几个“坑”(C++类相关)

淺唱寂寞╮ 提交于 2020-01-18 06:58:22
1、绝对不要自己手动地管理资源 2、一个裸的指针不要用两个shared_ptr管理,unique_ptr也是,两个指针是没有关联的都会认为是只有自己在用这个资源析构的时候会出错 3、用weak_ptr打破循环引用,parent和child 4、当需要在类的内部接口中,如果需要将this作为智能指针来使用的话,需要用该类派生自enable_shared_from_this 5、使用shared_ptr作为函数的接口,如果有可能尽量用const_shared_ptr&的模式 6、多线程模式下使用shared_ptr需要注意的事项 7、shared_ptr,weak_ptr和裸指针相比会大很多,并且效率上会有影响,尤其是在多线程模式下 一个shared_ptr在空间上至少是三个裸指针的大小(24个字节),本身有引用还要配合weak_ptr使用所以要保存多少该指针的引用。如下生成既有对象的new还有本身的new ObjectPtr obj4 = obj3进行拷贝时时间效率会慢很多 可以用以下方式减少空间 8、enable_shared_from_this和shared_from_this在构造和析构中是不能使用的,在某些情况下也不能使用,因为构造的时候类还未生成好,析构的时候类快完蛋了都没有意义 9、某些情况下,会出现内存不会降的问题,尤其是使用weak_ptr来处理循环引用的问题 10

c++:智能指针(weak_ptr)

房东的猫 提交于 2020-01-16 00:54:14
1.weak_ptr到底是什么? 简单的说就是weak_ptr是shared_ptr的一个助手,是为了配合shared_ptr而引入的一种智能指针,它指向一个由shared_ptr管理的对象而不影响所指对象的生命周期,也就是将一个weak_ptr绑定到一个shared_ptr不会改变shared_ptr的引用计数。不论是否有weak_ptr指向,一旦最后一个指向对象的shared_ptr被销毁,对象就会被释放。 2.为什么需要weak_ptr? 多个shared_ptr实例可以指向同一个动态对象,并维护了一个共享的引用计数器。对于引用计数法实现的计数,总是避免不了循环引用(或环形引用)的问题,这个时刻就需要智能指针 weak_ptr 例子: #include <iostream> #include <memory> #include <vector> using namespace std; class ClassA { public: ClassA() { cout << "ClassA Constructor..." << endl; } ~ClassA() { cout << "ClassA Destructor..." << endl; } shared_ptr<ClassB> pb; // 在A中引用B }; class ClassB { public: ClassB()

C++智能指针

杀马特。学长 韩版系。学妹 提交于 2020-01-13 22:10:21
开始接触C++的项目开发,初步了解OSG(OpenSceneGraph)三维渲染引擎。图形学的知识是大二阶段接触的,也有点遗憾后来的毕设没有继续往这方面研究。现在有点像是朝花夕拾,不过也得上了。确实图形学离不开数学,再次接触还是一堆图元,四元数之类的概念问题。可能就因为这些,C++让人觉得难以接触。今天看了一些资料,下次记录一下在OSG封装下构造基本图形。这次主要介绍一下智能指针。 当时N哥做技术培训时候,这个新词感觉很有意思。下面的链接讲的很细 https://www.cnblogs.com/wxquare/p/4759020.html 这里要注意的是在用智能指针定义数组,需要把这个指针存放在堆里面 比如下面的例子 osg::ref_ptr<osg::ShapeDrawable> shape3 = new osg::ShapeDrawable; 目前对于OSG的了解有限,感觉智能指针和引用计数为0时释放内存这两点比较一直贯穿其中。之后的具体理解再进行补充 来源: CSDN 作者: OPMR 链接: https://blog.csdn.net/sexgeek/article/details/103963062

【C++】智能指针详解

我的梦境 提交于 2020-01-09 16:08:58
智能指针 :将对内存的管理交付给对象,当对象析构时就能够清理资源,有效的避免内存泄露问题。(因为原生态指针(T*)管理资源时,若用户忘记释放内存,则可能会导致资源泄露。) 下面介绍四种智能指针 头文件均为#include< memory> 一.auto_ptr智能指针 C++98中经历过两次版本更新。 C++11中保留第一版auto_ptr。 1.首先介绍智能指针的三大结构 1.RAII:利用对象生命周期来控制内存资源,构造时获取资源,析构时释放资源。 特点:不需要显式释放资源。对象所需资源在其生命周期内始终有效。 2.重载运算符 * (解引用) -> 3.拷贝构造方法/重载=运算符方法,所产生的浅拷贝问题。 2.auto_ptr第一版本模拟实现 解决浅拷贝:通过 资源转移 的方法,一份资源只能由一个指针管理。之前的指针设置为空。 #include<iostream> using namespace std; template <class T> class auto_ptr1 { public: //1.RAII: auto_ptr1(T* ptr=nullptr) :_ptr(ptr) {} //2.重载* -> 运算符 T& operator *() { return *_ptr; } T& operator ->() { return _ptr; } //3.拷贝构造

智能指针

↘锁芯ラ 提交于 2020-01-07 08:53:23
1.智能指针的分类    shared_ptr 允许多个指针指向同一个对象    unique_ptr 只允许唯一指针指向指定对象    weak_ptr 弱引用,指向 shared_ptr 所管理的对象   智能指针都定义在 memory 头文件中 2.shared_ptr   shared_ptr 是模板,创建时,必须提供指针指向的类型:     shared_ptr<string> p1; // shared_ptr 可以指向string     shared_ptr<list<int>> p2; // shared_ptr 可以指向 int 的 list   默认初始化的智能指针中保存着一个空指针 3.make_shared 函数   shared_ptr<int> p3 = make_shared<int>(42); // 指向一个值为 42 的 int 的shared_ptr   shared_ptr<string> p4 = make_shared<string>(5, 's'); // 指向一个值为 “sssss” 的 string   shared_ptr<int> p5 = make_shared<int>(); // 指向一个值为 0 的 int   auto p6 = make_shared<vector<string>>(); // 指向一个动态分配的空

C++智能指针

无人久伴 提交于 2020-01-06 23:00:07
智能指针的由来: 除了静态内存和栈内存外,每个程序还有一个内存池,这部分内存被称为自由空间或者堆。程序用堆来存储动态分配的对象即那些在程序运行时分配的对象,当动态对象不再使用时,我们的代码必须显式的销毁它们。 在C++中,动态内存的管理是用一对运算符完成的:new和delete,new:在动态内存中为对象分配一块空间并返回一个指向该对象的指针,delete:指向一个动态独享的指针,销毁对象,并释放与之关联的内存。 动态内存管理经常会出现两种问题:一种是忘记释放内存,会造成内存泄漏;一种是尚有指针引用内存的情况下就释放了它,就会产生引用非法内存的指针。 为了更加容易(更加安全)的使用动态内存,引入了智能指针的概念。智能指针的行为类似常规指针,重要的区别是它负责自动释放所指向的对象。标准库提供的两种智能指针的区别在于管理底层指针的方法不同,shared_ptr允许多个指针指向同一个对象,unique_ptr则“独占”所指向的对象。标准库还定义了一种名为weak_ptr的伴随类,它是一种弱引用,指向shared_ptr所管理的对象,这三种智能指针都定义在memory头文件中。 shared_ptr 共享所有权,允许多个指针指向同一个对象,其内部有一个关联的引用计数,用来记录有多少个其他的shared_ptr指向相同的对象,当引用计数为0时将调用析构函数释放对应空间。 make

c++ 智能指针

匆匆过客 提交于 2019-12-27 21:37:25
【推荐】2019 Java 开发者跳槽指南.pdf(吐血整理) >>> 1 auto_ptr。智能指针销毁的时候自动delete所包含的指针。对象只能被一份智能指针持有。通过智能指针的复制构造函数会将前一个的指针置为null 使用方式如下: class Person{ std::string name; public: Person() :name("kk"){ std::cout<<"construct Person"<<std::endl; } ~Person(){ std::cout<<"deconstruct Person"<<std::endl; } void show(){ std::cout<<"show person: " + name<<std::endl; } void show1(){ std::cout<<"show person" <<std::endl; } }; auto_ptr<Person> ptr(new Person()); ptr->show();//ok ptr.get()->show();//ok auto_ptr<Person> ptr1= ptr; ptr1->show();//ok ptr->show();//错误。一旦通过ptr1= ptr复制后,智能指针包含的的指针即被清空变为null了(注意这个地方若是改为ptr->show1