【C++ techniques】Smart Pointers智能指针
Smart Pointers智能指针
看起来、用起来、感觉起来像内置指针,但提供更多的机能。拥有以下各种指针行为的控制权:
- 构造和析构;
- 复制和赋值;
- 解引。
Smart Pointers的构造、赋值、析构
C++的标准程序库提供的auto_ptr template:
auto_ptr对象是个smart pointer,用来指向诞生于堆内的对象,直到该auto_ptr被销毁为止;当销毁发生时,auto_ptr的析构函数会删除其所指物。
template<class T>
class auto_ptr
{
public:auto_ptr(T* ptr):pointee(ptr){}~auto_ptr(){delete pointee;}...
private:T* pointee;
};
在“同一对象只可被一个auto_ptr拥有”的前提下,上述做法可以有效运作;但当auto_ptr被复制或被赋值,其“对象拥有权”会转移:
template<class T>
class auto_ptr
{
public:...auto_ptr(auto_ptr<T>& rhs);auto_ptr<T>& operator = (auto_ptr<T>& rhs);...
}; template<class T>
auto_ptr<T>::auto_ptr(auto_ptr<T>& rhs)
{pointee = rhs.pointee; //将*pointee的拥有权转移至*thisrhs.pointee = 0; //rhs不再拥有任何东西
}template<class T>
auto_ptr<T>& auto_ptr<T>::operator = (auto_ptr<T>& rhs)
{if(this = &rhs)return *this;delete pointee; //必须删除目前拥有之物pointee = rhs.pointee;rhs.pointee = 0;return *this;
}
由于auto_ptr的复制构造函数被调用时,对象拥有权转移了,所以以by value方式传递auto_ptrs绝对不合适,Pass-by-refrence-to-const才是适当的途径。
void printTreeNode(ostream& s,auto_ptr<TreeNode> p)
{s << *p;
}int main()
{auto<TreeNode> ptn(new TreeNode);...printTreeNode(cout,ptn); //以by value方式传递auto_ptr
}//Pass-by-refrence-to-const方式
void printTreeNode(ostream& s, const auto_ptr<TreeNode>& p)
{s << *p;
}
实现Dereferencing Operators(解引操作符)
smart pointers的核心:operator*和operator->函数
//operator*
template<class T>
T& SmartPtr<T>::operator*() const
{///perform "smart pointer" processing;return *pointee;
}
//返回值是reference形式
//operator->
void editTuple(DBPtr<Tuple>& pt)
{LogEntry<Tuple> entry(*pt);do{pt->displayEditDialog();//会被编译器解释为(pt.operator->())->displayEditDialog();}while (pt->isValid == false)
}
//大部分时候想要operator->返回一个普通的dump pointer:
template<class T>
T* SmartPtr<T>::operator->() const
{//perform "smart pointer" processing;return pointee;
}
测试Smart Pointers是否为NULL
为smart pointer classes加上一个isNull函数很容易,但smart pointers 无法像dumb pointers那般自然地测试是否为null:
SmartPtr<TreeNode> ptn;
...
if(ptn == 0) ... //错误
if(ptn) ... //错误
if(!ptn) ... //错误
提供一个类型转换操作符,允许上述动作得以通过编译:
template<class T>
class SmartPtr
{
public:...operator void*(); //如果dumb ptr是null,返回零//否则返回非零值
};SmartPtr<TreeNode> ptn;
...
if(ptn == 0) ... //ok
if(ptn) ... //ok
if(!ptn) ... //ok
缺点:允许你把smart pointers拿来和完全不同的类型做比较:
SmartPtr<Apple> pa;
SmartPtr<Orange> po;
...
if(pa == po) //竟然可以过关//重载“!操作符”
template<class T>
class SmartPtr
{
public:...bool operator!() const; //只有当smart ptr是null才返回true...
};//clients:
SmartPtr<TreeNode> ptn;
...
if(!ptn)
{...
}else{...
}if(ptn == 0) ... //错误
if(ptn) ... //错误//唯一的风险:
SmartPtr<Apple> pa;
SmartPtr<Orange> po;
...
if(!pa == !po) //竟然可通过编译
C++标准库中,“隐式转换为void*”已被“隐式转换为bool”取代,而operator bool总是返回operator!的反相。
将Smart Pointers转换为Dumb Pointers
如果为smart pointer-to-T template加上一个隐式类型转换函数,便可转换为dumb pointer-to-T:
Template<class T>
class DBPtr
{
public:...operator T*() const; //新增的转换操作符...
};DBPtr<Tuple> pt;
...
normalize(pt); //现在这就成功了//nullness测试问题也一并解决了:
if(ptn == 0) ... //可以
if(ptn) ... //可以
if(!ptn) ... //可以
与设计smart pointer目的相违背!也不要提供对dumb pointer的隐式转换操作符,除非不得已!
Smart Pointers和“和继承有关的”类型转换
我们真正想要知道的是如何能够将“smart pointers classes的行为”在“与继承相关类型转换”上,能够和dumb pointers一样。答案很简单:不能够。
smart pointers虽然smart,却不是pointers,我们所能做的最好情况就是使用member templates来产生转换函数,然后再在其中出现模棱两可的时候使用转型动作。
Smart Pointers 与 const
smart pointers中const只能施行于指针身上,不能用于其所指的对象;
类型转换如果涉及const,便是一条单行道:从non-const 转换成const是安全的,从const 转换成non-const则不安全。此外,能够对const做的任何事情,也都可以对non-const指针进行。
和public inheritance的规则类似,可以利用:
实现smart pointers时令一个smart pointer-to-T class公开继承一个对应的smart pointer-to-const-T class:
template<class T>
class SmartPtrToConst
{
public:... //一般都会有smart pointer member//functionsprotected:union{const T* constPointee; //给SmartPtrToConst使用T* pointee; //给SmartPtr使用};
};template<class T>
class SmartPtr:public SmartPtrToConst<T>
{... //没有data members
}
相关文章:
【C++ techniques】Smart Pointers智能指针
Smart Pointers智能指针 看起来、用起来、感觉起来像内置指针,但提供更多的机能。拥有以下各种指针行为的控制权: 构造和析构;复制和赋值;解引。 Smart Pointers的构造、赋值、析构 C的标准程序库提供的auto_ptr template: au…...
LabVIEW利用以太网开发智能液位检测仪
LabVIEW利用以太网开发智能液位检测仪 目前,工业以太网接口在国内外的发展已经达到了相当深入的程度,特别是在自动化控制和工业控制领域有着非常广泛的应用。在工业生产过程中,钢厂的连铸机是前后的连接环节,其中钢水从大钢包进入…...
文字转语音:语音合成(Speech Synthesis) 数组文字循环播放
前言: HTML5中和Web Speech相关的API实际上有两类,一类是“语音识别(Speech Recognition)”,另外一个就是“语音合成(Speech Synthesis)”, 这两个名词实际上指的分别是“语音转文字”,和“文字变语音”。 speak() –…...
Spark基础
一、spark基础 1、为什么使用Spark Ⅰ、MapReduce编程模型的局限性 (1) 繁杂 只有Map和Reduce两个操作,复杂的逻辑需要大量的样板代码 (2) 处理效率低 Map中间结果写磁盘,Reduce写HDFS,多个Map通过HDFS交换数据 任务调度与启动开销大 (…...
localhost和127.0.0.1都可以访问项目,但是本地的外网IP不能访问
使用localhost和127.0.0.1都可以访问接口,比如: http://localhost:8080/zhgl/login/login-fy-list或者 http://127.0.0.1:8080/zhgl/login/login-fy-list返回json {"_code":10000,"_msg":"Success","_data":…...
快速掌握批量合并视频
在日常的工作和生活中,我们经常需要对视频进行编辑和处理,而合并视频、添加文案和音频是其中常见的操作。如何快速而简便地完成这些任务呢?今天我们介绍一款强大的视频编辑软件——“固乔智剪软件”,它可以帮助我们轻松实现批量合…...
OpenCV利用Camshift实现目标追踪
目录 原理 做法 代码实现 结果展示 原理 做法 代码实现 import numpy as np import cv2 as cv# 读取视频 cap cv.VideoCapture(video.mp4)# 检查视频是否成功打开 if not cap.isOpened():print("Error: Cannot open video file.")exit()# 获取第一帧图像&#x…...
使用pywin32读取doc文档的方法及run输出乱码 \r\x07
想写一个读取doc文档中表格数据,来对文档进行重命名。经查资料,py-docx无法读取doc文档,原因是这种是旧格式。所以,采用pywin32来进行读取。 import win32com.client as win32word win32.gencache.EnsureDispatch(Word.Applicati…...
一天一八股——TCP保活keepalive和HTTP的Keep-Alive
TCP属于传输层,关于TCP的设置在内核态完成 HTTP属于用户层的协议,主要用于web服务器和浏览器之间的 http的Keep-Alive都是为了减少多次建立tcp连接采用的保持长连接的机制,而tcp的keepalive是为了保证已经建立的tcp连接依旧可用(双端依旧可以…...
头部品牌停业整顿,鲜花电商的中场战事迎来拐点?
鲜花电商行业再次迎来标志性事件,曾经4年接连斩获6轮融资的明星品牌花加,正式宣布停业整顿。 梳理来看,2015年是鲜花电商赛道的发展爆发期,彼时花加等品牌相继成立,并掀起一波投资热潮,据媒体统计…...
深入解读redis的zset和跳表【源码分析】
1.基本指令 部分指令,涉及到第4章的api,没有具体看实现,但是逻辑应该差不多。 zadd <key><score1><value1><score2><value2>... 将一个或多个member元素及其score值加入到有序集key当中。根据zslInsert zran…...
elasticsearch内存占用详细分析
内存占用 ES的JVM heap按使用场景分为可GC部分和常驻部分。 可GC部分内存会随着GC操作而被回收; 常驻部分不会被GC,通常使用LRU策略来进行淘汰; 内存占用情况如下图: common space 包括了indexing buffer和其他ES运行需要的clas…...
【研究生学术英语读写教程翻译 中国科学院大学Unit3】
研究生学术英语读写教程翻译 中国科学院大学Unit1-Unit5 Unit3 Theorists,experimentalists and the bias in popular physics理论家,实验家和大众物理学的偏见由于csdn专栏机制修改,请想获取资料的同学移步b站工房,感谢大家支持!研究生学术英语读写教程翻译 中国科学院大学…...
基于虚拟同步发电机控制的双机并联Simulink仿真模型
💥💥💞💞欢迎来到本博客❤️❤️💥💥 🏆博主优势:🌞🌞🌞博客内容尽量做到思维缜密,逻辑清晰,为了方便读者。 ⛳️座右铭&a…...
微信小程序开发——自定义堆叠图
先看效果图 点击第一张图片实现折叠,再次点击实现展开 思路 图片容器绑定点击事件获取当前图片索引,触发onTap函数,根据索引判断当前点击的图片是否为第一张,并根据当前的折叠状态来更新每张图片的位置,注意图片向上…...
国庆day5
QT实现TCP服务器客户端搭建的代码 ser.h #ifndef SER_H #define SER_H#include <QWidget> #include<QTcpServer> #include<QTcpSocket> #include<QMessageBox> #include<QList> QT_BEGIN_NAMESPACE namespace Ui { class …...
经典算法----迷宫问题(找出所有路径)
目录 前言 问题描述 算法思路 定义方向 回溯算法 代码实现 前言 前面我发布了一篇关于迷宫问题的解决方法,是通过栈的方式来解决这个问题的(链接:经典算法-----迷宫问题(栈的应用)-CSDN博客)ÿ…...
macOS下 /etc/hosts 文件权限问题修复方案
文章目录 前言解决方案权限验证 macOS下 etc/hosts 文件权限问题修复 前言 当在 macOS 上使用 vi编辑 /etc/hosts 文件时发现出现 Permission Denied 的提示,就算在前面加上 sudo 也照样出现一样的提示,解决方案如下; 解决方案 可以尝试使用如下命令尝试解除锁定; sudo chf…...
【星海出品】ansible入门(二) playbook
核心是管理配置进行批量节点部署。 执行其中的一些列tasks。 playbook由YAML语言编写。 YAML的格式如下: 文件名应该以 .yml 结尾 1.文件的第一行应该以“—”(三个连字符)开始,表明YAML文件的开始。 2.在同一行中,#之…...
Spring Boot对账号密码进行加密储存
未来避免明文硬编码,我们需要对密码进行加密保存,例如账号密码 方法 在Spring Boot中,可以使用Jasypt(Java Simplified Encryption)库来对敏感信息进行加密和解密。Jasypt提供了一种简单的方式来在应用程序中使用加密…...
MPNet:旋转机械轻量化故障诊断模型详解python代码复现
目录 一、问题背景与挑战 二、MPNet核心架构 2.1 多分支特征融合模块(MBFM) 2.2 残差注意力金字塔模块(RAPM) 2.2.1 空间金字塔注意力(SPA) 2.2.2 金字塔残差块(PRBlock) 2.3 分类器设计 三、关键技术突破 3.1 多尺度特征融合 3.2 轻量化设计策略 3.3 抗噪声…...
云原生核心技术 (7/12): K8s 核心概念白话解读(上):Pod 和 Deployment 究竟是什么?
大家好,欢迎来到《云原生核心技术》系列的第七篇! 在上一篇,我们成功地使用 Minikube 或 kind 在自己的电脑上搭建起了一个迷你但功能完备的 Kubernetes 集群。现在,我们就像一个拥有了一块崭新数字土地的农场主,是时…...
Cursor实现用excel数据填充word模版的方法
cursor主页:https://www.cursor.com/ 任务目标:把excel格式的数据里的单元格,按照某一个固定模版填充到word中 文章目录 注意事项逐步生成程序1. 确定格式2. 调试程序 注意事项 直接给一个excel文件和最终呈现的word文件的示例,…...
Keil 中设置 STM32 Flash 和 RAM 地址详解
文章目录 Keil 中设置 STM32 Flash 和 RAM 地址详解一、Flash 和 RAM 配置界面(Target 选项卡)1. IROM1(用于配置 Flash)2. IRAM1(用于配置 RAM)二、链接器设置界面(Linker 选项卡)1. 勾选“Use Memory Layout from Target Dialog”2. 查看链接器参数(如果没有勾选上面…...
Nginx server_name 配置说明
Nginx 是一个高性能的反向代理和负载均衡服务器,其核心配置之一是 server 块中的 server_name 指令。server_name 决定了 Nginx 如何根据客户端请求的 Host 头匹配对应的虚拟主机(Virtual Host)。 1. 简介 Nginx 使用 server_name 指令来确定…...
ElasticSearch搜索引擎之倒排索引及其底层算法
文章目录 一、搜索引擎1、什么是搜索引擎?2、搜索引擎的分类3、常用的搜索引擎4、搜索引擎的特点二、倒排索引1、简介2、为什么倒排索引不用B+树1.创建时间长,文件大。2.其次,树深,IO次数可怕。3.索引可能会失效。4.精准度差。三. 倒排索引四、算法1、Term Index的算法2、 …...
k8s业务程序联调工具-KtConnect
概述 原理 工具作用是建立了一个从本地到集群的单向VPN,根据VPN原理,打通两个内网必然需要借助一个公共中继节点,ktconnect工具巧妙的利用k8s原生的portforward能力,简化了建立连接的过程,apiserver间接起到了中继节…...
大数据学习(132)-HIve数据分析
🍋🍋大数据学习🍋🍋 🔥系列专栏: 👑哲学语录: 用力所能及,改变世界。 💖如果觉得博主的文章还不错的话,请点赞👍收藏⭐️留言Ǵ…...
.Net Framework 4/C# 关键字(非常用,持续更新...)
一、is 关键字 is 关键字用于检查对象是否于给定类型兼容,如果兼容将返回 true,如果不兼容则返回 false,在进行类型转换前,可以先使用 is 关键字判断对象是否与指定类型兼容,如果兼容才进行转换,这样的转换是安全的。 例如有:首先创建一个字符串对象,然后将字符串对象隐…...
Redis的发布订阅模式与专业的 MQ(如 Kafka, RabbitMQ)相比,优缺点是什么?适用于哪些场景?
Redis 的发布订阅(Pub/Sub)模式与专业的 MQ(Message Queue)如 Kafka、RabbitMQ 进行比较,核心的权衡点在于:简单与速度 vs. 可靠与功能。 下面我们详细展开对比。 Redis Pub/Sub 的核心特点 它是一个发后…...
