当前位置: 首页 > news >正文

条款3:尽量使用const

文章目录

  • const指针和函数声明
    • const修饰指针
    • const修饰函数
    • const修饰容器
    • const应用在函数中
  • const限定成员函数
  • 避免const重载的代码重复
  • 总结

const指针和函数声明

const修饰指针

char greeting[] = "Hello";
char* p = greeting; 	// non-const 指针,// non-const 数据
const char* p = greeting; 	// non-const 指针,// const 数据
char* const p = greeting; // const 指针,// non-const 数据
const char* const p = greeting; // const 指针,// const 数据

 如果const出现在左侧:指向的是常量,const出现在右侧:指针本身是常量。

const修饰函数

void f1(const Widget* pw); // f1接受一个指向常量Widget对象的指针
void f2(Widget const* pw); // f2也一样

 const出现在类型的左边,或右边是等效的。

const修饰容器

std::vector<int> vec;
//...// iter 的行为像 T* const
const std::vector<int>::iterator iter = vec.begin();
*iter = 10; 	// 可以修改指向的数据
++iter; 	// 错误! iter 本身是 const
//cIter 的行为像 const T*
std::vector<int>::const_iterator cIter =vec.begin();
*cIter = 10; 	// 错误! *cIter 是 const
++cIter; 	// 正确, 可以修改迭代器本身

const应用在函数中

 令函数返回一个常量值,往往可以降低因客户错误而造成的意外,下面是一个有理数的例子。

class Rational {  }; // 有理数! 
const Rational operator*(const Rational& lhs, const Rational& rhs);

如果不小心把=写成了==

Rational a, b, c;
(a * b) = c; 	// 对a*b的结果调用operator=
if (a* b = c)  // 糟糕, 写错了,应该是 ==

 但这时候,由于我们返回的是一个const类型的,所以该做法在编译的时候就会提示错误,这也能让我们更快的找到错误。

const限定成员函数

在成员函数上使用const:
1、使类的接口意图更明确。知道哪些函数可以修改一个对象,哪些不能,这很重要。
2、使得使用const对象成为可能。
 C++的一个重要特性:仅在常量上不同的成员函数可以被重载。考虑表示文本块的类:

class TextBlock {
public:TextBlock(std::string str) {text = str;}const char& operator[](std::size_t position) const // const对象的operator[]{return text[position];} char& operator[](std::size_t position) // non-const对象的operator[]{return text[position];} 
private:std::string text;
};void print(const TextBlock& ctb) // 在这个函数中,ctb是const
{std::cout << ctb[0]; // 调用const的TextBlock::operator[]
}//TextBlock的运算符[]可以这样使用:
TextBlock tb("Hello");std::cout << tb[0]; // 调用non-const的TextBlock::operator[]const TextBlock ctb("World");
std::cout << ctb[0]; // 调用const的TextBlock::operator[]print(tb);   // 调用const的TextBlock::operator[]
print(ctb);  // 调用const的TextBlock::operator[]tb[0] = 'x'; //正确
ctb[0] = 'x'; //错误

避免const重载的代码重复

 假设TextBlock中的[]运算符不仅返回对适当字符的引用,还执行边界检查,记录访问信息,甚至可能进行数据完整性验证。

class TextBlock {
public:...const char& operator[](std::size_t position) const{... // do bounds checking... // log access data... // verify data integrityreturn text[position];}char& operator[](std::size_t position) {... // do bounds checking... // log access data... // verify data integrityreturn text[position];}
private:std::string text;
};

这边我们定义了一个const版本和一个非const版本的函数。
替代方案:让operator[]的一个版本调用另一个版本。先写const版本,然后脱离const限制。

class TextBlock {
public:...const char& operator[](std::size_t position) const{// 和前面一样.........return text[position];}char& operator[](std::size_t position){//只需要调用const版本return const_cast<char&>( //对op[]的返回类型抛弃const;//给*this的类型添加const;调用op的const版本[]static_cast<const TextBlock&>(*this)[position] );}...
};

1、在这种情况下,去掉返回值上的const是安全的,因为调用非const操作符[]的人首先必须有一个非const对象。
2、让非const操作符[]调用const版本是避免代码重复的安全方法。

总结

  • 声明const可以借助编译器检测使用错误。const可以应用于任何作用域的对象、函数参数和返回类型,以及作为一个整体的成员函数。
  • 编译器强制执行位常量,但你应该使用逻辑常量进行编程。
  • 当const和非const成员函数具有本质上相同的实现时,可以通过让非const版本调用const版本来避免代码重复。

相关文章:

条款3:尽量使用const

文章目录 const指针和函数声明const修饰指针const修饰函数const修饰容器const应用在函数中 const限定成员函数避免const重载的代码重复总结 const指针和函数声明 const修饰指针 char greeting[] "Hello"; char* p greeting; // non-const 指针,// non-const 数据…...

Chromadb词向量数据库总结

简介 Chroma 词向量数据库是一个用于自然语言处理&#xff08;NLP&#xff09;和机器学习的工具&#xff0c;它主要用于词嵌入&#xff08;word embeddings&#xff09;。词向量是将单词转换为向量表示的技术&#xff0c;可以捕获单词之间的语义和语法关系&#xff0c;使得计算…...

Gin之GORM 操作数据库(MySQL)

GORM 简单介绍 GORM 是 Golang 的一个 orm 框架。简单说&#xff0c;ORM 就是通过实例对象的语法&#xff0c;完成关系型数据库的操作的技术&#xff0c;是"对象-关系映射"&#xff08;Object/Relational Mapping&#xff09; 的缩写。使用 ORM框架可以让我们更方便…...

二十七、读写文件

二十七、读写文件 27.1 文件类QFile #include <QCoreApplication>#include<QFile> #include<QDebug>int main(int argc, char *argv[]) {QCoreApplication a(argc, argv);QFile file("D:/main.txt");if(!file.open(QIODevice::WriteOnly | QIODe…...

flutter 代码混淆

Flutter 应用混淆&#xff1a; Flutter 应用的混淆非常简单&#xff0c;只需要在构建 release 版应用时结合使用 --obfuscate 和 --split-debug-info 这两个参数即可。 –obfuscate --split-debug-info 用来指定输出调试文件的位置&#xff0c;该命令会生成一个符号映射表。目前…...

05 Vue中常用的指令

概述 All Vue-based directives start with a v-* prefix as a Vue-specific attribute. 所有基于 Vue 的指令都以 v-* 前缀作为 Vue 特有的属性。 v-text The v-text directive has the same reactivity as with interpolation. Interpolation with {{ }} is more perform…...

Mr. Cappuccino的第67杯咖啡——MacOS通过PD安装Win11

MacOS通过PD安装Win11 下载ParallelsDesktop安装ParallelsDesktop激活ParallelsDesktop下载Windows11安装Windows11激活Windows11 下载ParallelsDesktop ParallelsDesktop下载地址 安装ParallelsDesktop 关闭上面的窗口&#xff0c;继续操作 激活ParallelsDesktop 关闭上面的…...

【云原生kubernets】Service 的功能与应用

一、Service介绍 在kubernetes中&#xff0c;pod是应用程序的载体&#xff0c;我们可以通过pod的ip来访问应用程序&#xff0c;但是pod的ip地址不是固定的&#xff0c;这也就意味着不方便直接采用pod的ip对服务进行访问。为了解决这个问题&#xff0c;kubernetes提供了Service资…...

docker安装Prometheus

docker安装Prometheus Docker搭建Prometheus监控系统 环境准备(这里的环境和版本是经过测试没有问题,并不是必须这个版本) 主机名IP配置系统说明localhost随意2核4gCentOS7或者Ubuntu20.0.4docker版本23.0.1或者24.0.5,docker-compose版本1.29 安装Docker Ubuntu20.0.4版本…...

了解 Flutter 3.16 功能更新

作者 / Kevin Chisholm 我们在季度 Flutter 稳定版发布会上带来了 Flutter 3.16&#xff0c;此版本包含诸多更新: Material 3 成为新的默认主题、为 Android 带来 Impeller 的预览版、允许添加适用于 DevTools 的扩展程序等等&#xff0c;以及同步推出 Flutter 休闲游戏工具包重…...

python之画动态图 gif效果图

import pandas as pd import matplotlib import matplotlib.pyplot as plt import os# set up matplotlib is_ipython inline in matplotlib.get_backend() if is_ipython:from IPython import displayplt.ion()def find_csv_files(directory):csv_files [] # 用于存储找到的…...

【JavaWeb】用注解代替配置文件

WebServlet("/query") public class QueryServlet extends HttpServlet {...}在Servlet类上写WebServlet("query"),就相当于在配置文件里写了↓ <servlet><servlet-name>query</servlet-name><servlet-class>QueryServlet</se…...

SpringBoot 3.0 升级之 Swagger 升级

文章目录 SpringFox3.0.0openapi3Swagger 注解迁移ApiApiOperationApiImplicitParamApiModelApiModelProperty 最近想尝试一下最新的 SpringBoot 项目&#xff0c;于是将自己的开源项目进行了一些升级。 JDK 版本从 JDK8 升级至 JDK17。SpringBoot 版本从 SpringBoot 2.7.3 升…...

AR游戏开发

增强现实&#xff08;Augmented Reality&#xff0c;AR&#xff09;游戏是一种整合了虚拟和现实元素的游戏体验。玩家通过使用AR设备&#xff08;如智能手机、AR眼镜或平板电脑&#xff09;来与真实世界互动&#xff0c;游戏中的数字内容与真实环境相结合。以下是一些关于AR游戏…...

Easy Excel生成复杂下Excel模板(下拉框)给用户下载

引言 文件的下载是一个非常常见的功能&#xff0c;也有一些非常好的框架可以使用&#xff0c;这里我们就介绍一种比较常见的场景&#xff0c;下载Excel模版&#xff0c;导入功能通常会配有一个模版下载的功能&#xff0c;根据下载的模版&#xff0c;填充数据然后再上传。 需求…...

基于EasyExcel的数据导入导出

前言&#xff1a; 代码复制粘贴即可用&#xff0c;主要包含的功能有Excel模板下载、基于Excel数据导入、Excel数据导出。 根据实际情况修改一些细节即可&#xff0c;最后有结果展示&#xff0c;可以先看下结果&#xff0c;是否是您想要的。 台上一分钟&#xff0c;台下60秒&a…...

电子学会C/C++编程等级考试2021年06月(六级)真题解析

C/C++等级考试(1~8级)全部真题・点这里 第1题:逆波兰表达式 逆波兰表达式是一种把运算符前置的算术表达式,例如普通的表达式2 + 3的逆波兰表示法为+ 2 3。逆波兰表达式的优点是运算符之间不必有优先级关系,也不必用括号改变运算次序,例如(2 + 3) * 4的逆波兰表示法为* +…...

智能优化算法应用:基于供需算法3D无线传感器网络(WSN)覆盖优化 - 附代码

智能优化算法应用&#xff1a;基于供需算法3D无线传感器网络(WSN)覆盖优化 - 附代码 文章目录 智能优化算法应用&#xff1a;基于供需算法3D无线传感器网络(WSN)覆盖优化 - 附代码1.无线传感网络节点模型2.覆盖数学模型及分析3.供需算法4.实验参数设定5.算法结果6.参考文献7.MA…...

vue3 setup语法糖写法基本教程

前言 官网地址&#xff1a;Vue.js - 渐进式 JavaScript 框架 | Vue.js (vuejs.org)下面只讲Vue3与Vue2有差异的地方&#xff0c;一些相同的地方我会忽略或者一笔带过与Vue3一同出来的还有Vite&#xff0c;但是现在不使用它&#xff0c;等以后会有单独的教程使用。目前仍旧使用v…...

利用两个指针的差值求字符串长度

指针和指针也可以相加减&#xff0c;例如定义一个一维数组arr[10]&#xff1b;再定义一个指针&#xff08;int *p&#xff09;指向数组首元素的地址&#xff0c;定义一个指针&#xff08;int* q&#xff09;指向数组最后一个元素的地址&#xff0c;那么q-p的结果就是整个数组的…...

生成xcframework

打包 XCFramework 的方法 XCFramework 是苹果推出的一种多平台二进制分发格式&#xff0c;可以包含多个架构和平台的代码。打包 XCFramework 通常用于分发库或框架。 使用 Xcode 命令行工具打包 通过 xcodebuild 命令可以打包 XCFramework。确保项目已经配置好需要支持的平台…...

大数据学习栈记——Neo4j的安装与使用

本文介绍图数据库Neofj的安装与使用&#xff0c;操作系统&#xff1a;Ubuntu24.04&#xff0c;Neofj版本&#xff1a;2025.04.0。 Apt安装 Neofj可以进行官网安装&#xff1a;Neo4j Deployment Center - Graph Database & Analytics 我这里安装是添加软件源的方法 最新版…...

UDP(Echoserver)

网络命令 Ping 命令 检测网络是否连通 使用方法: ping -c 次数 网址ping -c 3 www.baidu.comnetstat 命令 netstat 是一个用来查看网络状态的重要工具. 语法&#xff1a;netstat [选项] 功能&#xff1a;查看网络状态 常用选项&#xff1a; n 拒绝显示别名&#…...

基于PHP的连锁酒店管理系统

有需要请加文章底部Q哦 可远程调试 基于PHP的连锁酒店管理系统 一 介绍 连锁酒店管理系统基于原生PHP开发&#xff0c;数据库mysql&#xff0c;前端bootstrap。系统角色分为用户和管理员。 技术栈 phpmysqlbootstrapphpstudyvscode 二 功能 用户 1 注册/登录/注销 2 个人中…...

MySQL 索引底层结构揭秘:B-Tree 与 B+Tree 的区别与应用

文章目录 一、背景知识&#xff1a;什么是 B-Tree 和 BTree&#xff1f; B-Tree&#xff08;平衡多路查找树&#xff09; BTree&#xff08;B-Tree 的变种&#xff09; 二、结构对比&#xff1a;一张图看懂 三、为什么 MySQL InnoDB 选择 BTree&#xff1f; 1. 范围查询更快 2…...

【Veristand】Veristand环境安装教程-Linux RT / Windows

首先声明&#xff0c;此教程是针对Simulink编译模型并导入Veristand中编写的&#xff0c;同时需要注意的是老用户编译可能用的是Veristand Model Framework&#xff0c;那个是历史版本&#xff0c;且NI不会再维护&#xff0c;新版本编译支持为VeriStand Model Generation Suppo…...

【UE5 C++】通过文件对话框获取选择文件的路径

目录 效果 步骤 源码 效果 步骤 1. 在“xxx.Build.cs”中添加需要使用的模块 &#xff0c;这里主要使用“DesktopPlatform”模块 2. 添加后闭UE编辑器&#xff0c;右键点击 .uproject 文件&#xff0c;选择 "Generate Visual Studio project files"&#xff0c;重…...

es6+和css3新增的特性有哪些

一&#xff1a;ECMAScript 新特性&#xff08;ES6&#xff09; ES6 (2015) - 革命性更新 1&#xff0c;记住的方法&#xff0c;从一个方法里面用到了哪些技术 1&#xff0c;let /const块级作用域声明2&#xff0c;**默认参数**&#xff1a;函数参数可以设置默认值。3&#x…...

算法打卡第18天

从中序与后序遍历序列构造二叉树 (力扣106题) 给定两个整数数组 inorder 和 postorder &#xff0c;其中 inorder 是二叉树的中序遍历&#xff0c; postorder 是同一棵树的后序遍历&#xff0c;请你构造并返回这颗 二叉树 。 示例 1: 输入&#xff1a;inorder [9,3,15,20,7…...

python读取SQLite表个并生成pdf文件

代码用于创建含50列的SQLite数据库并插入500行随机浮点数据&#xff0c;随后读取数据&#xff0c;通过ReportLab生成横向PDF表格&#xff0c;包含格式化&#xff08;两位小数&#xff09;及表头、网格线等美观样式。 # 导入所需库 import sqlite3 # 用于操作…...