首页 > 编程语言 >c++ weak_ptr

c++ weak_ptr

时间:2022-12-11 12:33:37浏览次数:35  
标签:mName weak c++ Person s2 shared ptr

 weak_ptr

(1)weak_ptr指向一个shared_ptr指向的对象,且不会改变对象的引用计数。

(2)weak_ptr不控制所指对象的生命周期,不拥有所有权。

(3)不能调用->和解引用*

weak_ptr使用场景

 (1)A类中有一个需求需要存储其它A类的对象信息,如果使用shared_ptr,这样会造成循环依赖,所以我们需要使用一个不需要拥有所有权的指针来标记这个同类对象。

可以通过lock来提升为shared_ptr(类型装换)。

通过一个示例简单认识一下

int main() {

    shared_ptr<Person> s1 = make_shared<Person>();
    // weak_ptr是需要和shared_ptr一起来用的
    weak_ptr<Person> w1{ s1 };

    // 结果都是1 计数器不会增加
    cout << "s1->count=" << s1.use_count() << endl;
    cout << "w1->count=" << w1.use_count() << endl;
    // 结果都是2 lock将其提升为shared_ptr(类型装换)。计数器会增加
    shared_ptr<Person> s2 = w1.lock();
    cout << "s1->count=" << s1.use_count() << endl;
    cout << "w1->count=" << w1.use_count() << endl;
    cout << "s2->count=" << s2.use_count() << endl; 
    return 0;
}

结果:

 

 

 比如A类中有一个需求需要存储其它A类的对象信息,如果使用shared_ptr,这样会造成循环依赖,通过例子看一下:

 

#include <stdio.h>
#include <iostream>
#include <algorithm>
#include <vector>
#include<Windows.h>  
using namespace std;


//自定义数据类型
class Person {
public:
    Person(string name, int age) {
        mName = name;
        mAge = age;
    }

    Person();

    ~Person()
    {
        cout << mName << "调用析构函数" << endl;
    }

    void Set_Name(string name)
    {
        this->mName = name;
    }

    void Info()
    {
        std::cout << "name:" << this->mName << endl;
    }

    // 在这里定义一个unique_ptr的别名UniquePtr
    using UniquePtr = unique_ptr<Person>; 
    string mName;
    int mAge;
    void Set_Friend(shared_ptr<Person> s) {
        _friend = s;
    }

private: 
    shared_ptr<Person> _friend;
};

unique_ptr<Person> GetUniquePtr()
{
    unique_ptr<Person> u1 = make_unique<Person>();
    u1->Set_Name("测试");
    return u1;
}

int main() {

    shared_ptr<Person> s1 = make_shared<Person>();
    s1->mName = "s1";
    shared_ptr<Person> s2 = make_shared<Person>();
    s2->mName = "s2";
    shared_ptr<Person> s3 = make_shared<Person>();
    s3->mName = "s3";
    s2->Set_Friend(s3);
    s3->Set_Friend(s2);

    return 0;
}

Person::Person()
{
}

结果:

 

 就会发现s2,s3没有释放

我们通过weak_ptr来解决:

#include <stdio.h>
#include <iostream>
#include <algorithm>
#include <vector>
#include<Windows.h>  
using namespace std;


//自定义数据类型
class Person {
public:
    Person(string name, int age) {
        mName = name;
        mAge = age;
    }

    Person();

    ~Person()
    {
        cout << mName << "调用析构函数" << endl;
    }

    void Set_Name(string name)
    {
        this->mName = name;
    }

    void Info()
    {
        std::cout << "name:" << this->mName << endl;
    }

    // 在这里定义一个unique_ptr的别名UniquePtr
    using UniquePtr = unique_ptr<Person>; 
    string mName;
    int mAge;
    void Set_Friend(shared_ptr<Person> s) {
        _friend = s;
    }

private: 
    weak_ptr<Person> _friend;
};

unique_ptr<Person> GetUniquePtr()
{
    unique_ptr<Person> u1 = make_unique<Person>();
    u1->Set_Name("测试");
    return u1;
}

int main() {

    shared_ptr<Person> s1 = make_shared<Person>();
    s1->mName = "s1";
    shared_ptr<Person> s2 = make_shared<Person>();
    s2->mName = "s2";
    shared_ptr<Person> s3 = make_shared<Person>();
    s3->mName = "s3";
    s2->Set_Friend(s3);
    s3->Set_Friend(s2);

    return 0;
}

Person::Person()
{
}

 

 结果:

 

 

总结:shared_ptr在环形引用中,带来了循环引用的弊端,所以,需要将其中一个设置为弱引用(根据实际情况确定,一般将管理者使用shared_ptr,)weak_ptr。

  

标签:mName,weak,c++,Person,s2,shared,ptr
From: https://www.cnblogs.com/anjingdian/p/16973405.html

相关文章

  • C++:类模板知识回顾
    概述类的私有、公有、类继承有时并不能满足我们的开发需求,尤其是将类作为容器(泛型编程)使用时,因此类模板在C++随之衍生。相关概念也会在下文中一一阐述~模板类的定义与使......
  • C++学习---cstdio的源码学习分析04-创建临时文件函数tmpfile
    cstdio中的文件操作函数stdio.h中定义了文件删除函数remove,文件重命名函数rename,创建临时文件函数tmpfile,生成临时文件名函数tmpnam。接下来我们一起来分析一下tmpfile对应......
  • C++
    通讯录管理系统1、系统需求通讯录是一个可以记录亲人、好友信息的工具。本教程主要利用C++来实现一个通讯录管理系统系统中需要实现的功能如下:添加联系人:向通讯录中......
  • C/C++外卖点餐管理程序
    C/C++外卖点餐管理程序2、外卖点餐管理程序设计一个外卖点餐系统,要求餐厅管理员可以输入菜品信息(编号,菜名,价格,数量....),顾客可以根据菜品信息下单(订餐人,电话,菜品列表......
  • c++ l理解智能指针
     智能指针概述C++的指针包括原始指针和智能指针两种,智能指针是原始指针的封装,其优点是可以自动分配内存,无需担心内存的泄露。并不是所有的指针都可以封装为智能指针,很多......
  • C++停车场管理方案的数据结构设计
    C++停车场管理方案的数据结构设计题目5:停车场管理方案的数据结构设计[问题描述]停车场是一条可以停放n辆车的狭窄车道,并且只有一个大门是车的出入口。汽车停放按照到达......
  • C/C++《程序设计与算法综合实践》备选题目
    C/C++《程序设计与算法综合实践》备选题目《程序设计与算法综合实践》期末大作业题目及评分标准有如下情况之一者,为不及格。(1)未能完成所选题目评分标准的最低要求。(2)......
  • c++中的字符集与中文(宽字符)
    首先要来说一说字符集和编码的关系,这两者既有交叉、又有异同。​​https://www.runoob.com/w3cnote/charset-encoding.html​​就非西欧字符而言,比如中国以及港澳台......
  • C++日期和时间编程总结
    在C++11之前,C++编程只能使用C-style日期时间库,其精度只有秒级别,这对于有高精度要求的程序来说,是不够的。但这个问题在C++11中得到了解决,C++11中不仅扩展了......
  • C++手机运动信息管理系统
    C++手机运动信息管理系统《程序设计基本能力综合实训》实训案例名称:手机运动信息管理系统-----说明文档本案例主要完成手机运动信息的管理。主要功能包括:用户信息的......