C++ 手写智能指针 shared_ptr

c++之智能指针 智能指针是C++中的一种智能指针类型,它具有自动管理内存的能力。智能指针类型可以帮助程序员减少手动管理内存分配和释放的编程错误,并增强程序的可靠性和可维护性。智能指针在C++标准库中提供了三种类型:std::unique_ptr、std::shared_ptr和std::weak_ptr。 阅读详情

一、实现时的一些需要考虑的点

  1. 对于构造函数,我们仿照了shared_ptr的源代码,加入了explicit关键字,防止原始指针隐式的转化为智能指针。
  2. 传入空指针或者使用默认构造函数时,引用计数为0。
  3. 拷贝赋值函数需要检查自赋值的情况。
  4. 释放动态内存时时刻注意两个指针是不是空指针。

二、智能指针shared_ptr实现

#include <iostream>
#include <memory>

using namespace std;

template<typename T>
class my_shared_ptr {
private:
	size_t* _useCnt;  
	T* _ptr;

public:
	// 默认构造函数
	my_shared_ptr() : _ptr(new T), _useCnt(new size_t(0)) {}

	// 构造函数
	explicit my_shared_ptr(T* p) : _ptr(p),  _useCnt(new size_t){
		if (p) {
			*_useCnt = 1;
		} else {
			*_useCnt = 0;
		}
	}

	// 拷贝构造函数
	my_shared_ptr(const my_shared_ptr& rhs) {
		_ptr = rhs._ptr; // 指向同一块内存
		_useCnt = rhs._useCnt;
		(*_useCnt)++; // 引用计数增加	
	}

	// 拷贝赋值函数,注意检查自赋值
	my_shared_ptr& operator= (const my_shared_ptr& rhs) {
		if (this != &rhs) {			// 检查自赋值
			if (_ptr) {				// 防止自身原来指向空指针,_useCnt>0说明确实是指向实体的
				--(*_useCnt);		// 自己要被rhs覆盖了,引用计数减1
				// 如果没有引用计数了,把自己清空,释放动态内存
				if (*_useCnt == 0) {
					delete _useCnt;
					delete _ptr;
				}
				// 把自己变成rhs, 引用计数加一
				_useCnt = rhs._useCnt;
				_ptr = rhs._ptr;
				++(*_useCnt);
			}
		}
		return *this;
	}


	// 得到计数
	int use_count() {
		return *_useCnt;
	}
	
	~my_shared_ptr() {
		if (!_ptr || (*_useCnt == 1)) { // 只有当前指针指向空或者只有一个指向对象时释放内存
			delete _useCnt;
			delete _ptr;
		} else {  // 否则只减少引用计数
			--(*_useCnt);
		}
	}
};


int main() {

	// 检查构造函数是否正常工作
	my_shared_ptr<int> p1(new int(1));
	cout << "p1 cnt:" << p1.use_count() << endl;

	// 检查拷贝构造是否正常工作
	{
		my_shared_ptr<int> p2(p1);
		cout << "p2 cnt:" << p2.use_count() << endl;
		cout << "p1 cnt:" << p1.use_count() << endl;
	}
	
	// 检查引用计数是否正常工作
	cout << "p1 cnt:" << p1.use_count() << endl;

	// 检查默认初始化时计数是否正常
	my_shared_ptr<int> p4;
	cout << "p4 cnt:" << p4.use_count() << endl;

	// 检查拷贝赋值是否正常工作
	p4 = p1;
	cout << "p1 cnt:" << p1.use_count() << " p4 cnt:" << p4.use_count() << endl;

	return 0;
}
C++11 shared_ptr手写---面试常考 共享对其所指堆内存空间的所有权,当最后⼀个指涉到该对象的shared_ptr不再指向他时,shared_ptr会⾃动析构所指对象如何判断⾃⼰是否指涉到该资源的最后⼀个?《引⽤计数》shared_ptr构造函数,使引⽤计数++析构函数,–赋值运算符,sp1 = sp2;sp1++,sp2–移动构造函数,会将源shared_ptr置空,所引引⽤计数不变,所以移动操作⽐复制快(复制要递增引⽤计数,移动不需要)引⽤计数使得shred_ptr⼤小是裸指针的2。 阅读详情

相关推荐

现代C++之手写智能指针

现代C++之手写智能指针0.回顾所有代码还是放在仓库里面,欢迎star!https://github.com/Light-City/CPlusPlusThings前面一节编写了一个RAI...

编程与实战的博客 1575

手写shared_ptr智能指针

#include <string> #include <iostream> using namespace std; template <typename T> class Sharedptr { public: //空参数构造, 空指针 Sharedptr():count(0), ptr((T*) 0){} //构造函数 count 必须new出来 Sharedptr(T* p) : count(new int(1)), ptr(p){} //拷贝构造函.

qq_24624539的博客 2863

从零到一:YT8512C PHY芯片在STM32F407上的LWIP移植实战与避坑指南

本文详细介绍了YT8512C PHY芯片在STM32F407平台上基于LWIP协议栈的移植实战,涵盖硬件连接、CubeMX配置、寄存器定制和调试技巧。重点解析了与主流PHY芯片的差异,提供了完整的避坑指南和优化建议,帮助开发者快速实现稳定可靠的嵌入式网络连接。

uber9的博客 538

智能指针1: 手写简单的智能指针(对普通指针进行封装)

智能指针(1): 手写简单的智能指针(对普通指针进行封装)

yubaoaihh 572

电力现货交易市场-报价方式

电是一种能源,也是一种商品,既然是商品自然可以在市场中进行自由交易。

qq_38225433的博客 5117

IEC 104电力规约详细解读(一) - 报文结构、报文分类、ASDU

比如,双方可以按频率发送,比如接收8帧I帧回答一帧S帧,也可以要求接收1帧I帧就应答1帧S帧,当然也可以不要求(S帧内容示例参考例1)。所以U帧格式的控制欲第一个字节就只有6种情况,分别是0x83(TESTER确认)、0x43(TESTER命令)、0x23(STOPDT确认)、0x13(STOPDT命令)、0x0B(START确认)、0x07(START命令)ASDU(应用服务数据单元),协议原文格式最好去101协议去看看,会比较详细。遥信、遥测、遥控、遥调、总召、对时等都需要使用I格式传送。

张二狗的博客 1万+

(C++) 手写智能指针(unique_ptr;share_ptr)

RAII资源获取即初始化 C++11更是弥补了auto_ptr的缺陷,提出了unique_ptr,share_ptr,weak_ptr 注意智能指针的本质就是一个模板类,通过类的内部的操作,来管理资源 本文简单实现了一下

cuber-lotus的博客 1885

【全志V821_FoxPi】6-2 IMX219 MIPI摄像头适配

全志V821芯片适配IMX219 MIPI摄像头(2lane)教程,基于FoxPi开发板V1.2 SDK。文章详细介绍了IMX219的技术参数(800万像素、1/4英寸CMOS、支持1080P@30fps输出)及模组接口原理图。重点展示了设备树配置方法,包括PIO引脚定义(TWI0使用PA3/PA4,复位引脚PA2)、TWI0节点设置(100kHz时钟)以及VIND0节点中sensor0的完整配置(I2C地址0x20、MCLK0、RAW格式输出等)。配置过程强调需注意IMX219的器件地址转换(0x10→0

第四维度的博客 2248

c++ 手写智能指针shared_ptr

c++ 手写智能指针shared_ptr 留个坑,回头在填。 #include <utility> #include <iostream> #include <cstddef> #include <string> template<typename T> class shared_ptr { friend class shared_ptr; public: shared_ptr(T* ptr = nullptr) :

qq_37294304的博客 1378

UWB 多传感器通信的纳秒无线位置和时钟同步方法

利用UWB高精度的特点,实现多节点下的无线时钟同步和定位。通过优化硬件架构,减少不确定延迟的影响,系统可以提供纳秒级时钟同步消息

DT程序员的博客 1324

【漏洞复现】Apache Tomcat远程代码执行漏洞(CVE-2024-56337)

CVE-2024-56337是一个存在于Apache Tomcat中的TOCTOU(Time-of-Check Time-of-Use)竞争条件漏洞。此漏洞源于对先前漏洞(CVE-2024-50379)的不完整修复。若默认servlet是可写的(参数readonly设置值为false,该设置为非默认设置)表示不区分大小写文件系统,在负载下并发读取和上传同一文件可以绕过Tomcat的大小写检查。攻击者可以通过构造恶意请求上传含恶意JSP代码的文件,使其触发解析并执行这些文件,从而导致远程代码执行。

李同學AI安全 3195

C++智能指针面试手写unique_ptr和shared_ptr

【代码】C++智能指针面试手写unique_ptr和shared_ptr。

weixin_43676247的博客 126

QCM2290 PM-3 如何让mirco-usb支持关机充电

PM4125-3插入type-C触发开机进入关机充电的CC脚中断条件是否可以软件上屏蔽, 做到只通过VBUS中断即可触发进入关机充电模式,达到和PM4125-2的效果一样只要插入micro USB 就可以触发进入关机充电模式。硬件团队提议修改寄存器 SCHG_L_MISC_SYSOK_CFG 0x164A bit[4] 目前修改如下 — a/BOOT.XF.4.1/boot_images/QcomPkg/Library/PmicLib/target/Agatti_pmCocos/psi/pm_confi

墨染天玑的博客 441

【面试总结】C++手写智能指针shared_ptr

Hello!ଘ(੭ˊᵕˋ)੭昵称:海轰标签:程序猿|C++选手|学生简介:因C语言结识编程,随后转入计算机专业,获得过国家奖学金,有幸在竞赛中拿过一些国奖、省奖…已保研学习经验:扎实基础 + 多做笔记 + 多敲代码 + 多思考 + 学好英语!唯有努力💪本文仅记录自己感兴趣的内容。

海到无边天作岸 山登绝顶我为峰 1273

AI视频生成工作流开发:从产品拆解到带货视频全流程实现

本文介绍了一套完整的AI视频生成工作流开发方案,该系统能够自动分析产品素材并生成9个标准化分镜,支持白底图智能替换,最终输出专业带货视频。系统基于Coze平台搭建,整合豆包大模型及多模态生成模型,实现从产品分析、脚本生成到视频合成的全流程自动化。关键模块包括产品特征提取、智能分镜分配、视觉内容生成和用户交互调整,支持手动优化提示词和输出结果。该方案采用模块化设计,结合多种AI模型协同工作,为电商视频制作提供高效解决方案。

huanghm88的专栏 383

Data-Structures-and-Algorithm-Analysis-in-Java.pdf

作者: Weiss, Mark A. 出版社: Addison Wesley Data Structures and Algorithm Analysis in Java is an “advanced algorithms” book that fits between traditional CS2 and Algorithms Analysis courses. In the old ACM Curriculum Guidelines, this course was known as CS7. This text is for readers who want to learn good programming and algorithm analysis skills simultaneously so that they can develop such programs with the maximum amo...

现代C++⊂C++11篇(六)智能指针演进与手写shared_ptr:从RAII到定制删除器

本文围绕C++智能指针的演进与实现展开。从RAII思想切入,梳理auto_ptr的致命缺陷、unique_ptr的独占改进,再到shared_ptr的共享设计。重点手写shared_ptr核心:引用计数管理、拷贝构造、赋值运算符重载及析构逻辑,并引入function包装器实现灵活的定制删除器。通过逐行构建,读者可透彻理解智能指针的底层机制,为后续攻克内存碎片化、循环引用及线程安全等工程难题打下坚实基础。

沫漓的博客 420

VC中sqlite的使用

在VC中对sqlite的使用,实现数据库大批数据的快速插入,读取数据库中的数据在ListCtrl中显示

【C++面试】手写智能指针(三):weak_ptr如何解决shared_ptr循环引用

weak_ptr 本身并不拥有资源,它主要用于观察由 shared_ptr 管理的对象,并且不会增加强引用计数。它最经典的用途,就是解决 shared_ptr 之间的循环引用问题。本文从循环引用为什么会导致内存泄漏开始,手写一个简化版 MyWeakPtr,并介绍弱引用计数、lock()、expired() 以及控制块的基本设计。

qq_64148519的博客 209

Devexpress16.2.6破解工具

Devexpress16.2.6破解工具Devexpress16.2.6破解工具Devexpress16.2.6破解工具Devexpress16.2.6破解工具

TMS_WebGMaps_1.9.8.0_Full_Source

TMS_WebGMaps_1.9.8.0_Full_Source 全源码 delphi cbuilder

C++智能指针shared_ptr实现原理与手写教程

在C++编程中,内存管理是核心挑战之一,原生指针的直接使用常伴随内存泄漏、悬垂指针等风险。为解决这一问题,现代C++引入了RAII(资源获取即初始化)设计理念,通过对象的生命周期自动管理资源。基于RAII原则,智能指针技术应运而生,它通过封装原生指针并在析构时自动释放资源,实现了内存的安全管理。其中,引用计数是实现资源共享的关键机制,它允许多个智能指针安全地指向同一对象,并在最后一个引用消失时自动清理资源。这一机制在工程实践中价值显著,尤其适用于对象所有权不明确或需要多上下文共享资源的场景,如缓存系统、复杂

congjukun0600的博客 411

C++ 深入智能指针

学习记录

学习记录 1620

C++智能指针

每多一个shared_ptr对资源进行管理,引用计数将+1,每个指向改对象的shared_ptr对象销毁时,引用计数-1。作为对auto_ptr的改进,unique_ptr对其持有的资源对象具有唯一控制权,即不可以通过常规的复制语法转移或拷贝资源对象的控制权。weak_ptr是一个不控制资源对象的智能指针,也不会影响资源的引用计数,其主要的目的是协助shared_ptr工作。通过weak_ptr的构造函数,参数传入一个持有资源对象的shared_ptr对象或weak_ptr对象,即可创建。

新手嵌入式学习的博客 1598

智能指针(shared_ptr, weak_ptr, unique_ptr)

c++ 中的智能指针让 c++ 看起来像 java,go 这种带 GC 的语言,但和 GC 又不完全相同。c++ 中的智能指针使用引用计数,当引用计数减为 0 的时候就会立即释放资源,释放资源具有实时性;而像 java,go 这样的 GC 语言,当对象不被引用时,可能不会立即释放资源,资源的释放有滞后性。如果不使用智能指针,需要开发者使用 new 和 delete 创建和销毁对象。使用智能指针,开发者不需要手动来释放资源,当引用计数变为 0 时自动释放。就这一个好处。

weixin_38184628的博客 1110

shared_ptr与weak_ptr的手写实现

C++11的智能指针是RAII(Resource Acquisition Is Initialization)机制的一种体现。详细的介绍请参见原文原文1 对RAII的介绍请参见这里原文2 考察较多的就是shared_ptr的手写实现了,这里不是源码,只是模拟实现。 template<class T> //模板 class Share_ptr { // weak_ptr的friend friend class Weak_ptr<T>; //这里先不用在意,稍后解释 p

不算太晚 915

手写一个智能指针:从 unique_ptr 到 shared_ptr 的引用计数原理

智能指针是现代 C++ 内存管理的核心工具。RAII 提供了思想基础,unique_ptr 定义了清晰的独占所有权语义,shared_ptr 则通过引用计数实现了安全的共享模型,而 weak_ptr 负责解决循环引用这一经典难题。真正理解并掌握这些智能指针的实现原理,才能在工程实践中写出健壮、高性能、可维护的 C++ 代码。

qq_29426201的博客 760

手写shared_ptr、vector、string

手写vector #include<iostream> using namespace std; template<typename T> class myvec { private: T* data; int capacity; int size; public: myvec()//构造函数 { data = NULL; capacity = size = 0; } myvec(int len) { data = new T[len]; capa

sdsfdsfdsds的博客 309

C++智能指针(一):从RAII思想到shared_ptr循环引用问题

本文深入探讨了C++智能指针的原理与应用。首先分析了手动内存管理的痛点(内存泄漏、野指针等问题),进而引入RAII设计思想,通过对象生命周期自动管理资源。随后详细解析了智能指针的本质:普通类对象+RAII+运算符重载模拟指针行为。重点介绍了unique_ptr的独占特性、移动语义及核心接口(get/release/reset),强调其轻量高效优势。文章为后续讲解shared_ptr、weak_ptr等高级特性奠定基础,系统性地揭示了C++智能指针的设计哲学与实现机制。全文以问题导向层层深入,既有理论阐述又包

2301_77799834的博客 376
上一篇: new、express new、operator new、placement new 之间的千丝万缕
下一篇: C++ AVL树手撕代码实现
zsiming
博客等级 码龄7年 43粉丝 74原创
评论 1
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

当前余额3.43元 前往充值 >
需支付:10.00元
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付元
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值