C++中类中const知识应用详解
下面将从**const
成员**、const
成员函数、const
对象、mutable
、constexpr
等方面,逐一详解 C++ 类中常见的 const
用法及注意事项,并配合示例。
一、const
数据成员
-
必须在初始化列表中初始化
class A {const int x; // const 成员 public:A(int v) : x(v) { } // ❌ 合法:初始化列表中初始化// A(int v) { x = v; } // ❌ 错误:无法在函数体内赋值 };
-
不可修改
- 一旦初始化,之后在对象生存期内不能再改变。
- 可用于对外保证成员不被篡改。
-
与静态成员结合
class B {static const int N = 100; // 类内常量,若需要 ODR 定义,则在 cpp 中:// const int B::N; };
static const
整数/枚举成员可在类内直接给初始值,不占实例空间。
二、const
成员函数
在成员函数后添加 const
,表明该函数不会修改任何非 mutable
成员,也不会调用非 const
成员函数。
class C {int x;
public:C(int v): x(v) {}int getX() const { // 常量成员函数return x; // 只能访问 x,不可修改}void setX(int v) { // 非 const 函数x = v;}
};
-
调用约束
const C c1(5); c1.getX(); // ✅ 可以调用 const 成员函数 // c1.setX(7); // ❌ 错误:不能调用非 const 成员函数
-
隐式
this
类型- 在
const
成员函数中,this
的类型为const C*
,保证不可修改成员。
- 在
三、const
对象
C obj1(3); // 普通对象
const C obj2(4); // 常量对象,只能调用 const 成员函数
-
只读语义:
obj2
的所有非static
数据成员对于外部都是只读的。 -
可与指针/引用混用:
void foo(const C& c); foo(obj1); // OK,将 obj1 作为只读参数
四、mutable
修饰符
当你希望在 const
成员函数中仍然修改某些成员,可将它们声明为 mutable
:
class Logger {mutable std::ostream& os; // 即使在 const 函数中也可修改
public:Logger(std::ostream& _os): os(_os) {}void log(const std::string& msg) const {os << msg << std::endl; // OK,os 是 mutable}
};
- 场景:缓存、延迟初始化、统计访问次数等。
五、constexpr
与常量表达式
C++11 起,可将成员函数或构造函数声明为 constexpr
,使其在编译期计算:
class Point {int x, y;
public:constexpr Point(int _x, int _y): x(_x), y(_y) {}constexpr int getX() const { return x; }constexpr int getY() const { return y; }
};constexpr Point p(1,2);
static_assert(p.getX() == 1, ""); // 在编译期验证
-
注意:
constexpr
成员函数 必须 同时 是const
(除了构造函数)。- 只有在满足编译期求值规则时才真正成为常量表达式。
六、与继承结合
struct Base {virtual void foo() const {// ...}
};
struct Derived : Base {void foo() const override { // 覆盖 const 成员函数// ...}
};
- 覆盖时签名要一致:返回类型、参数列表后是否
const
都要相同,否则不构成覆盖。
七、注意事项汇总
-
忘记在初始化列表中初始化
const
成员- 会导致编译错误。
-
在
const
成员函数中尝试修改非mutable
成员- 编译器会报错,防止越界修改。
-
constexpr
函数应当尽量简单- 包含循环与分支也支持,但要遵守常量表达式的限制。
-
不要滥用
mutable
- 可能破坏对象的逻辑常量性(logical constness),只在真正需要缓存、延迟初始化时使用。
-
接口设计
- 对于只读操作,应当标记为
const
;有副作用的操作,要去除const
,让常量对象无法调用。
- 对于只读操作,应当标记为
八、综合示例
#include <iostream>
#include <vector>class Matrix {const int rows, cols; // 必须初始化std::vector<double> data; // 默认构造mutable bool dirty; // 缓存标志
public:// constexpr 构造 + 初始化列表constexpr Matrix(int r, int c): rows(r), cols(c), data(r*c), dirty(true) {}// const 成员函数:只读访问double get(int i, int j) const {dirty = false; // OK:dirty 是 mutablereturn data[i*cols + j];}// 非 const 成员函数:修改void set(int i, int j, double v) {data[i*cols + j] = v;dirty = true;}constexpr int getRows() const { return rows; }constexpr int getCols() const { return cols; }bool isDirty() const { return dirty; }
};int main() {Matrix M(2,3);M.set(0,0,1.23);std::cout << M.get(0,0) << "\n"; // 可以修改 dirtystd::cout << std::boolalpha << M.isDirty() << "\n"; // falseconstexpr Matrix N(3,3);static_assert(N.getRows()==3, ""); // 编译期校验return 0;
}
相关文章:
C++中类中const知识应用详解
下面将从**const 成员**、const 成员函数、const 对象、mutable、constexpr 等方面,逐一详解 C 类中常见的 const 用法及注意事项,并配合示例。 一、const 数据成员 必须在初始化列表中初始化 class A {const int x; // const 成员 public:A(int v) :…...

【速写】KV-cache与解码的再探讨(以束搜索实现为例)
文章目录 1 Beam Search 解码算法实现2 实现带KV Cache的Beam Search解码3 关于在带kv-cache的情况下的use_cache参数 1 Beam Search 解码算法实现 下面是一个使用PyTorch实现的beam search解码算法: 几个小细节: 束搜索可以加入length_penalty&#…...

(网络)应用层协议-HTTPS
1.HTTPS是什么? HTTPS是应用层的一种协议,是在HTTP的基础上进行了加密层的处理。 HTTP协议的内容都是按照文本的形式进行传输的,所以呢就很容易被别人知道传输的是什么。 我们在了解了TCP/IP之后是知道我们的数据在传输的过程中是通过路由器进…...

vue3: pdf.js 3.4.120 using javascript
npm install pdfjs-dist3.4.120 项目结构: pdfjsViewer.vue <template><div><div v-if"loading" class"flex justify-center items-center py-8"><div class"animate-spin rounded-full h-12 w-12 border-b-2 borde…...
Spark目前支持的部署模式。
一、本地模式(Local Mode) 特点: 在单台机器上运行,无需集群。主要用于开发、测试和调试。所有组件(Driver、Executor)在同一个 JVM 中运行。 启动命令: bash spark-submit --master local[*]…...

想实现一个基于MCP的pptx生成系统架构图【初版实现】
技术栈:Python + MCP协议 + python-pptx + FastMCP 核心创新点:通过MCP协议实现PPTX元素的动态化生成与标准化模板管理 当前还是个半成品,后续持续更新。 主要先介绍一下思路。 一、MCP协议与系统设计原理 1.1 为什么选择MCP? 标准化工具调用:通过MCP将PPTX元素生成逻辑封…...

PyTorch Lightning实战 - 训练 MNIST 数据集
MNIST with PyTorch Lightning 利用 PyTorch Lightning 训练 MNIST 数据。验证梯度范数、学习率、优化器对训练的影响。 pip show lightning Version: 2.5.1.post0Fast dev run DATASET_DIR"/repos/datasets" python mnist_pl.py --output_grad_norm --fast_dev_run…...

力扣2094题解
记录: 2025.5.12 题目: 思路: 暴力遍历。 解题步骤: 1.统计数字出现次数:使用数组cnt来记录输入数组中每个数字的出现次数。 2.生成三位偶数:通过循环从100开始,每次递增2,生成…...

DHCP自动分配IP
DHCP自动分配IP 练习1 路由器 Router>en Router#conf t Router(config)#ip dhcp pool ip10 //创建DHCP地址池 Router(dhcp-config)#network 192.168.20.0 255.255.255.0 // 配置网络地址和子网掩码 Router(dhcp-config)#default-router 192.168.20.254 //配置默认网关 Rou…...
【CF】Day57——Codeforces Round 955 (Div. 2, with prizes from NEAR!) BCD
B. Collatz Conjecture 题目: 思路: 简单模拟 很简单的模拟,我们只需要快速的找到下一个离 x 最近的 y 的倍数即可(要大于 x) 这里我们可以这样写 add y - (x % y),这样就知道如果 x 要变成 y 的倍数还要…...

(done) 补充:xv6 的一个用户程序 init 是怎么启动的 ?它如何启动第一个 bash ?
先看 main.c 从函数名来看,比较相关的就 userinit() 和 scheduler() #include "types.h" #include "param.h" #include "memlayout.h" #include "riscv.h" #include "defs.h"volatile static int started 0;//…...
Nginx部署前端项目深度解析
在部署Vue前端项目时,Nginx的高效配置直接影响用户体验和性能表现。以下从7个关键维度深度解析部署方案,并提供专业级配置策略: 一、项目构建与基础部署 生产构建 npm run build -- --modern # 现代模式构建生成dist/目录包含:…...

超详细讲解C语言转义字符\a \b \r \t \? \n等等
转义字符 C语言有一组字符很特殊,叫做转义字符,顾名思义,改变原来的意思的字符。 1 \? ??)是一个三字母词,在以前的编译器它会被编译为] (??会被编译为[ 因此在以前输入(are you ok ??)就会被编译为are you ok ] 解决这个…...

SpringBoot校园失物招领信息平台
SpringBoot校园失物招领信息平台 文章目录 SpringBoot校园失物招领信息平台1、技术栈2、项目说明2.1、登录注册2.2、管理员端截图2.3、用户端截图 3、核心代码实现3.1、前端首页3.2、前端招领广场3.3、后端业务处理 1、技术栈 本项目采用前后端分离的架构,前端和后…...
【Qt/C++】深入理解 Lambda 表达式与 `mutable` 关键字的使用
【Qt/C】深入理解 Lambda 表达式与 mutable 关键字的使用 在 Qt 开发中,我们常常会用到 lambda 表达式来编写简洁的槽函数。今天通过一个实际代码示例,详细讲解 lambda 的语法、变量捕获方式,特别是 mutable 的作用。 示例代码 QPushButto…...
扩展:React 项目执行 yarn eject 后的 package.json 变化详解及参数解析
扩展:React 项目执行 yarn eject 后的 package.json 变化详解及参数解析 什么是 yarn eject?React 项目执行 yarn eject 后的 package.json 变化详解1. 脚本部分 Scripts 被替换2. 新增构建依赖 dependencies(部分)3. 新增 Babel …...
slackel系统详解
Slackel 是一个基于 Slackware Linux 和 Salix OS(另一个 Slackware 衍生版)的轻量级 Linux 发行版,主要面向桌面用户。它由希腊开发者 Dimitris Tzemos 创建,目标是结合 Slackware 的稳定性与用户友好的工具,同时优化…...

rust 全栈应用框架dioxus server
接上一篇文章dioxus全栈应用框架的基本使用,支持web、desktop、mobile等平台。 可以先查看上一篇文章rust 全栈应用框架dioxus👈 既然是全栈框架,那肯定是得有后端服务的,之前创建的服务没有包含后端服务包,我们修改…...
CSS Layer 详解
CSS Layer 详解 前言 最近在整理CSS知识体系时,发现Layer这个特性特别有意思。它就像是给样式规则提供了一个专属的「VIP通道」,让我们能更优雅地解决样式冲突问题。今天我就用最通俗的语言,带大家全面了解这个CSS新特性。 什么是CSS Laye…...

西安交大多校联训NOIP1模拟赛题解
西安交大多校联训NOIP1模拟赛题解 T1 秘境形式化题意思路代码(丑陋) T2 礼物形式化题意思路代码(实现) T3 小盒子的数论形式化题意思路代码(分讨) T4 猫猫贴贴(CF997E)形式化题意思路代码(深奥&…...

数据结构(三)——栈和队列
一、栈和队列的定义和特点 栈:受约束的线性表,只允许栈顶元素入栈和出栈 对栈来说,表尾端称为栈顶,表头端称为栈底,不含元素的空表称为空栈 先进后出,后进先出 队列:受约束的线性表࿰…...

若依定制pdf生成实战
一、介绍 使用 Java Apache POI 将文字渲染到 Word 模板是一种常见的文档自动化技术,广泛应用于批量生成或定制 Word 文档的场景。使用aspose可以将word转成pdf从而达到定制化pdf的目的。 参考文档:java实现Word转Pdf(Windows、Linux通用&a…...
RCE联系
过滤 绕过空格 ● 进制绕过 题目练习 数字rce 使用$0执行bash,<<<将后面的字符串传递给左边的命令。 例如: <?php highlight_file(__FILE__); function waf($cmd) { $whiteList [0, 1, 2, 3, 4, 5, 6, 7, 8, 9, \\, \, $, <]; $cmd_ch…...

c++STL-vector的模拟实现
cSTL-vector的模拟实现 vector的模拟实现基本信息构造函数析构函数返回容量(capacity)返回元素个数(size)扩容(reserve和resize)访问([])迭代器(**iterator**)…...
C++核心编程解析:模板、容器与异常处理全指南
文章目录 一、模板1.1 定义1.2 作用1.3 函数模版1.3.1 格式 1.4 类模版1.4.1 格式1.4.2 代码示例1.4.3 特性 二、容器2.1 概念2.2 容器特性2.3 分类2.4 向量vector2.4.1 特性2.4.2 初始化与操作2.4.3 插入删除 2.5 迭代器2.6 列表(list)2.6.1 遍历方式2.…...

在 Elasticsearch 中连接两个索引
作者:来自 Elastic Kofi Bartlett 解释如何使用 terms query 和 enrich processor 来连接 Elasticsearch 中的两个索引。 更多有关连接两个索引的查询,请参阅文章 “Elastic:开发者上手指南” 中的 “丰富数据及 lookup” 章节。 Elasticsea…...
Linux常用命令详解(下):打包压缩、文本编辑与查找命令
一、打包压缩命令 在Linux系统中,打包与压缩是文件管理的核心操作之一。不同的工具适用于不同场景,以下是最常用的命令详解: 1. tar命令 作用:对文件进行打包、解包、压缩、解压。 语法: tar [选项] [压缩包名] […...

使用 Watt toolkit 加速 git clone
一、前言 Watt toolkit 工具是我经常用于加速 GitHub 网页和 Steam 游戏商店访问的工具,最近想加速 git clone,发现可以使用 Watt toolkit 工具的代理实现。 二、查看端口 我这里以 Ubuntu 为例,首先是需要将加速模式设置为 System࿱…...

应急响应靶机——WhereIS?
用户名及密码:zgsf/zgsf 下载资源还有个解题.exe: 1、攻击者的两个ip地址 2、flag1和flag2 3、后门程序进程名称 4、攻击者的提权方式(输入程序名称即可) 之前的命令: 1、攻击者的两个ip地址 先获得root权限,查看一下历史命令记录&#x…...

Docke容器下JAVA系统时间与Linux服务器时间不一致问题解决办法
本篇文章主要讲解,通过docker部署jar包运行环境后出现java系统内时间与服务器、个人电脑真实时间不一致的问题原因及解决办法。 作者:任聪聪 日期:2025年5月12日 问题现象: 说明:与实际时间不符,同时与服务…...