C++ STL源码剖析 笔记补充

news2024/11/17 7:54:07

写在前面

简单记录一些《C++ STL源码剖析中》涉及到的C++语法和注意事项。

1. 静态常量成员在类内直接初始化

  • 如果含有const static integral类型的成员变量,可以在类内定义时直接初始化;
    静态成员初始化
  • 注意integral不只是int类型,而是包含所有的整型,如下所示:
    • short
    • char,特别注意char类型也是整型;
    • int
    • long
    • long long

一些关于staticconst约束的类内成员变量初始化要求:

  • 如果只是static成员变量,则只能类内定义,然后在类外初始化
  • 如果只是const成员变量,则可以在类内定义时初始化,也可以在构造函数中初始化,但一定要初始化
  • 如果是const static float/double则只能在类外初始化,且一定要初始化
  • const static integral可以在类内定义时初始化,也可以在类外初始化,但一定要初始化

可以参考博客:C++ 的类中static和const关键字声明变量的初始化方式总结

2. union类型

  • union是C/C++中的一种类型,类型中的所有变量共用同一段内存存储的起点均一致,大小为占用空间最大的变量的大小;
  • 因此一个union变量同一时间中只能存其中一个变量的值,其余变量的值均被覆盖(或至少覆盖一部分);
  • 目的是减少存储所需的空间,提高空间的利用率;
  • 一个例子如下:
    union类型
  • 上图中的objclient_data共用相同起始地址的一段空间,如下图所示:
    union类型结构示意
  • 但要注意尽量不要在union中定义C++风格的class类型对象,而是用C风格的struct或者基本类型,避免出错;
  • 可以参考博文:C++中的union介绍;
  • C风格的类型也被称为POD (Plain Old Data)类型,包括基本数据类型、指针、union、数组、POD的struct或者class;
  • POD的struct或者class需同时满足以下条件:
    • 不显式定义构造函数、拷贝构造函数、重载赋值函数和析构函数;
    • 类内无非静态非POD成员变量;
    • 无基类;

3. typedef用法

  • 用于为现有的类型创建一个新名字;
  • 只为类型增加别名,便于使用;
  • typedef并不创建新的类型,仅让新别名在编译时被解释,让编译器进行超越预处理器能力的文本替换而已;
  • 使用方法如下:
typedef existing_type new_type_name;
  • 和基本类型的使用,例如:
/*改写前*/
unsigned int a;
/*改写后*/
typedef unsigned int WORD;
WORD a;
  • 和指针的使用,例如:
/*改写前*/
char * str; 
/*改写后*/
typedef char * pstr; 
pstr str = "abc";
  • 和数组的使用,例如:
/*改写前*/
char line[81]; 
char text[81];
/*改写后*/
typedef char Line[81]; 
Line text, secondline;
  • 和函数指针的使用,例如:
void printHello(int i);
/*改写前*/
void (*pFunc)(int);
pFunc = &printHello;
(*pFunc)(110);
/*改写后*/
typedef void (*PrintHelloHandle)(int);
PrintHelloHandle pFunc;
pFunc = &printHello;
(*pFunc)(110);
  • 参考博文:typedef 用法总结;

4. typename用法

  • 作用是用来声明后面跟的name是类型名而不是变量名;
  • 在旧用法中是可以用class代替typename的;
  • 在泛型中的用法如下:
template<typename T>
class test_typename{
	//...
};
 
template<class T>
class test_class{
	//...
};
  • 但如果要在typedef中使用泛型元素,则必须使用typename加以声明,以表明元素为类型,因为typedef只能为类型赋别名;
  • 参考博文:typename的两种用法;

5. explicit用法

  • 只能修饰只有一个参数类构造函数
  • 作用是取消在类对象构造时自动的隐式转换,避免引起语义的漏洞,导致难以察觉的构造错误;
  • 一个例子如下:
class CxString   
{  
public:  
    char *_pstr;  
    int _size;  
    // 使用关键字explicit的类声明, 显式转换 
    // 限定了只能用以下方式调用:
    // CxString string1(24);
    // 以下调用无法通过编译:
    // CxString string2 = 10; // 相当于是将CxString string1(10)封装后再赋值给string2
    // CxString string3 = 'c'; // 相当于是将CxString string1(int('c'))封装后再赋值给string3
    explicit CxString(int size)  
    {  
        _size = size;  
        // ...  
    }  
};  
  • 可以参考博文:C++中的explicit详解;

6. 指针常量和常量指针

  1. 指针常量
  • 指针类型的常量;
  • int * const ptr
  • 指针的指向不可修改,在定义时必须同时初始化;
  • 但指针指向的空间内容可以修改;
  1. 常量指针
  • 指向常量的指针;
  • const int *ptr或者int const *ptr
  • 指针指向的空间内容不可修改;
  • 但指针的指向可以修改;

7. copy_backward()函数用法

  • copy()类似,用于复制一段序列,且只用于序列容器
  • 复制时从这段序列的尾部开始复制,避免覆盖后面的值;
  • 可以用于将某段序列整体后移,相比之下,copy()用于将序列整体前移

原理

8. void*指针

  • void*占据和其他指针相同空间大小,只是它的指向暂时还不明;
  • 可以强制转换成任何类型的指针,也可以赋值为任何类型的指针,如:
void *pv;

int i = 5;
int *pi = &i;

// 1. void*可以赋值为任意类型的指针
pv = pi;
// 但反过来不行
// pi = pv;  // 会出错
// 加上强制类型转换可以
pi = (int *)pv;

// 2. void*可以经过强制类型转换来使用
int j = *(int *)pv;
// 但一定要经过强制类型转换才能使用
// int j = *pv;  // 会出错
  • 取值不可以不经过强制转换;
  • 其他类型的指针也不可以用未经强制转换的void*赋值
  • 可以赋初始值为0或者nullptr
  • 如果作为函数的参数类型或者返回类型,则表示可以接收任意类型的指针或者可以返回任意类型的指针;
  • 相当于是普通类型指针的父类,用于实现多态或者充当泛型;
  • 可以参考博文:C++中的void*理解;

9. 自增和自减函数重载

  • 自增函数重载:
  • self& operator++() {}相当于++i,前置自增,先自增再返回
    • 返回的是自身的引用,可以作为左值和右值;
++i = a;  // 虽然这样写很奇怪
  • self operator++(int) {}相当于i++,后置自增,先返回再自增
    • 返回的是值,只能作为右值;
a = i++;
  • 其中的int是没有意义的,仅用于区分前置还是后置;
  • 自减函数重载同理;

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/195569.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

< 每日算法 - Javascript解析:经典弹珠游戏 >

每日算法 - JavaScript解析&#xff1a;弹珠游戏一、任务描述&#xff1a;》 示例一&#xff1a;》示例二二、题意解析三、解决方案&#xff1a;往期内容 &#x1f4a8;一、任务描述&#xff1a; 欢迎各位来到「力扣嘉年华」&#xff0c;接下来将为各位介绍在活动中广受好评的…

HSAF实战收获

收获1&#xff1a;MySQL数据类型对应Java类型表格这里的timestamp类型在Java中对应TimeStamp类型&#xff0c;varchar和char都是对饮的String类型收获2&#xff1a;TableFieldTableField(exist false) 注解加载bean属性上&#xff0c;表示当前属性不是数据库的字段&#xff0c…

[golang Web开发] 4.golang web开发:模板引擎

一.简介 使用 Go 的 Web 模板引擎需要以下两个步骤&#xff1a; (1).对文本格式的模板源进行语法分析&#xff0c;创建一个经过语法分析的模板结构&#xff0c;其中模板源既可以是一个字符串,也可以是模板文件中包含的内容 (2).执行经过语法分析的模板&#xff0c;将ResponseWr…

Django User模型

Django User模型用户管理自定义用户模型Django自定义验证引用User模型视图开发创建序列器创建视图创建路由用户注册注册序列化器注册视图注册路由用户管理 在开发登录功能的时候需要数据库来保存用户登录信息和状态&#xff0c;Django中有个内置app 名为 django.contrib.auth …

ICT是什么

信息与通信技术&#xff08;ICT&#xff0c;information and communications technology&#xff09;是一个涵盖性术语&#xff0c;覆盖了所有通信设备或应用软件&#xff1a;比如说&#xff0c;收音机、电视、移动电话、计算机、网络硬件和软件、卫星系统&#xff0c;等等&…

(1)Nginx简介和安装教程

目录 一、下载 二、报错提醒&环境安装 1、安装gcc编译器 2、安装perl库 3、安装 zlib库 4、也可通过命令进行统一安装 三、编译及安装 四、启动并访问 1、启动 2、访问 3、问题排查 五、安装成系统文件 一、下载 官网地址&#xff1a;nginx news Nginx官网提供…

OAuth2入门

1.下载资源 演示代码&#xff1a; OAuth2-example: 演示OAuth2的认证流程https://gitee.com/lisenaq/oauth2-example克隆下载到本地&#xff1a; 导入项目&#xff1a; client 客户 authorization-server 认证服务 resource-owner 资源所有者 resource-server 资源…

儿童台灯哪个品牌更护眼推荐?儿童书桌台灯品牌排行榜

不难发现&#xff0c;近些年我国儿童近视率增长迅速&#xff0c;随着生活条件越来越好&#xff0c;对电子章产品的普及非常广泛&#xff0c;每个家庭的孩子必不可少的就是伏案完成作业&#xff0c;这样的话就需要使用到台灯&#xff0c;选购台灯的时候最好选择适合儿童的专业护…

【算法基础】高精度加法

&#x1f466;个人主页&#xff1a;Weraphael ✍&#x1f3fb;作者简介&#xff1a;目前是C语言学习者 ✈️专栏&#xff1a;【C/C】算法 &#x1f40b; 希望大家多多支持&#xff0c;咱一起进步&#xff01;&#x1f601; 如果文章对你有帮助的话 欢迎 评论&#x1f4ac; 点赞…

一篇五分生信临床模型预测文章代码复现——FIgure 9.列线图构建,ROC分析,DCA分析 (三)

之前讲过临床模型预测的专栏,但那只是基础版本,下面我们以自噬相关基因为例子,模仿一篇五分文章,将图和代码复现出来,学会本专栏课程,可以具备发一篇五分左右文章的水平: 本专栏目录如下: Figure 1:差异表达基因及预后基因筛选(图片仅供参考) Figure 2. 生存分析,…

axios实战学习——使用高德地图api接口数据实现天气查询案例

文章目录&#x1f4cb;前言&#x1f3af;案例介绍&#x1f9e9;关于高德开发平台1️⃣创建应用生成Key2️⃣查看API文档&#x1f9e9;测试接口&#x1f3af;案例编写&#x1f3af;实现效果&#x1f4cb;前言 关于这个Vue axios 获取接口数据的操作&#xff0c;这篇文章就不过…

UniRx之基础入门

什么是Rx 官方ReactiveX简介&#xff1a; An API for asynchronous programming with observable streams。 通过这句话我们可以得到&#xff1a; 1.首先Rx是个编程接口&#xff0c;不同语言提供不同实现。例如JVM语言中的RxJava。 2.使用场景&#xff0c;异步编程中。 3.基…

路由器 内核开发 流程

宽 带上网已经不是什么新鲜事情&#xff0c;人们对相关的网络器件已经不再陌生&#xff0c;比如说常见的路由器。对于一般的网络用户&#xff0c;他们能知道怎样使用路由器来上网、玩游戏等就 已经感到很满足了&#xff0c;通常情况下对路由器的深层技术很少去过问研究&#xf…

Matlab和PCL中的点云滤波

而在PCL中总结了几种需要进行点云滤波处理的情况&#xff0c;这几种情况分别是&#xff1a; (1)点云数据密度不规则需要平滑。 (2)因为遮挡等问题造成离群点需要去除。 (3)大量数据需要进行“下采样”(Downsample)。 (4)噪声数据需要去除。 对应的解决方法是&#xff1a; (1)按…

什么是ITIL中的变更管理

商业环境和客户期望在不断变化&#xff0c;数字化转型已成为各行各业企业成功的关键因素。数字化转型的关键在于利用可用 应对业务挑战和抓住机遇的技术。当你分解它时&#xff0c;数字化转型基本上是信息技术管理更好地消除有问题的领域&#xff0c;并使您的 IT 基础架构能够应…

WebView缓存机制

一 前言 由于H5具备 开发周期短、灵活性好 的特点&#xff0c;所以现在 Android App大多嵌入了 Android Webview 组件进行 Hybrid 开发 但我知道你一定在烦恼 Android Webview 的性能问题&#xff0c;特别突出的是&#xff1a;加载速度慢 & 消耗流量 今天&#xff0c;我将…

Django 模型的继承

Django 模型的继承项目管理模型关联关系模块的包管理模型的继承项目管理 到目前为止&#xff0c;都是属于httprunner中的用例部分&#xff0c;针对核心功能进行的开发工作&#xff0c;要把平台做成一个用户可以使用的程度还需要些额外的功能&#xff0c;比如项目管理&#xff…

13薪| 8k-14k Java开发工程师

"众推职聘”以交付结果为宗旨的全流程化招聘服务平台&#xff01;今日招聘信息↓工作内容1.参与软件项目和产品概要设计&#xff0c;负责详细功能设计、编码实现及相关文档编写&#xff1b;2.根据模块设计完成相应的模块编码及单元测试&#xff1b;3.对用户行为、需求及反…

zeek集群简述

Zeek不是多线程的&#xff0c;因此&#xff0c;一旦达到单处理器内核的限制&#xff0c;当前唯一的选择就是将工作负载分散到多个内核&#xff0c;甚至多个物理计算机上。Zeek的集群部署场景是构建这些大型系统的当前解决方案。Zeek附带的工具和脚本提供了一种结构&#xff0c;…

自注意力和位置编码(比较卷积神经网络、循环神经网络和自注意力)

在自注意力中&#xff0c;查询、键和值都来自同一组输入。 卷积神经网络和自注意力都拥有并行计算的优势&#xff0c;而且自注意力的最大路径长度最短。但是因为其计算复杂度是关于序列长度的二次方&#xff0c;所以在很长的序列中计算会非常慢。 为了使用序列的顺序信息&…