C/C++:混肴点分析

news2024/9/29 9:34:16

C++中的常量介绍

字面常量

字面常量是指直接出现在代码中的常量值。例如,整数常量10、浮点数常量3.14、字符常量'A'等都属于字面常量。字面常量的值在编译时就已经确定,并且不能被修改。

字面常量存在类型,但没有地址

注意字符常量和只包含一个字符的字符串在 C/C++ 中有一些区别:

1.表示方式:字符常量使用单引号括起来,例如 'A',而只包含一个字符的字符串使用双引号括起来,例如 "A"。

2.类型:字符常量的类型是 char

3.存储方式:字符常量在内存中占用一个字节的空间,而只包含一个字符的字符串会分配n+1的空间(n个用于存储字符,一个用于存储字符串结束符 \0)。

4.使用上的差异:字符常量可以直接赋值给一个 char 变量,例如 char ch = 'A';。而字符串不能直接赋值给 char 变量,需要使用字符指针或字符数组来处理,例如 const char* str = "ABC";指针需要加const。

5.操作上的差异:对字符常量进行操作时,可以直接使用字符之间的运算符,例如 'A' + 1;而对只包含一个字符的字符串进行操作时,需要使用字符串相关的函数或操作方法,例如 strlen()、strcpy() 等。

符号常量

符号常量是通过标识符来表示的常量值,在程序中使用时要先进行定义。使用符号常量的好处是可以给常量起一个具有描述性的名字,方便理解和维护代码。在C++中,我们通常使用const关键字来定义符号常量。

在C++中,符号常量的定义语法有两种方式:使用#define预处理指令和使用const关键字。

1.使用#define预处理指令定义常量:

#define 常量名 值

例子:

#define PI 3.14159

#define MAX_VALUE 100

用#define定义的常量是在编译前进行文本替换,没有类型限制,可以用于定义任何类型的常量

2.使用const关键字定义常量:

const 类型 常量名 = 值;

例子:

const int MAX_VALUE = 100;

const double PI = 3.14159;

使用const定义的常量有类型限制,可以用于定义任何类型的常量,也可以用于定义对象常量

C++的const分析

1:C++和C的const实现原理对比

C语言中的const修饰的变量实际上还是一个变量,只是一个只读变量,是可以通过指针来改变,改变方法就是对这个const变量取地址,然后用指针指向它,去修改这个指针指向的内容,所以说C语言中const修饰的并不是真正意义上的常量,而是一个只读变量。但是有一种情况例外,就是C语言用const修饰的全局变量,编译器把它放在只读存储区里面。

 C++里面的const修饰的变量,编译器对它的处理,是把这个放在符号表里面,符号表就是一个二维表,里面有符号和对应的值。假设采用与C语言类似的方法取地址,然后改变指针指向的内容的方法,const变量的内存还位于栈区或者静态存储区,原先空间的值依旧会改变,但符号表里的值没变,打印结果也不会变。所以C++里面的const修饰的的确是常量,而不是只读变量,C++里面对const常量使用了extern,也会分配存储空间。

const int& b = 2;  // const int temp =2, const int& b=temp 
cout << &b << endl; //0000009086CFF524

const字符常量有空间,有地址

2:const与宏定义之间的区别

宏定义发生在预处理阶段,不会检查作用域和类型。这就是本质的区别。

void f()

{

    #define a 3

    const int b = 4;

}

void g()

{

    printf("a = %d\n", a);

    //printf("b = %d\n", b);

}

临时变量

临时变量是一种只在调用期间有效,且具有常性的变量,是字面常量。

字面常量有类型,但没地址

临时变量是如何产生的?

①传值返回

在main函数中我们调用add函数,add函数将sum的值返回,然后将sum的值赋值给re,可是当add函数调用一结束,sum作为add中的局部变量就会立即消亡,那么这个时候是如何将sum赋值给re的呢?

实际上这个时候临时变量就产生了关键的作用,编译器会创建一个临时变量,将sum的值拷贝给这个临时变量,返回的实际上是这个临时变量的值,函数调用结束将这个临时变量的值赋值给re。

②强制类型转换

强制类型转换一定会产生临时变量,因为编译器并不会对原变量进行强制类型转换,而是将原变量的值强制类型转换为所转类型的值,然后将强制类型转换后的值赋值给相应类型的临时变量,不会改变原变量的类型

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

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

相关文章

关于我写过那些MySQL专栏

写在文章开头 这是截至今日写过的文章汇总&#xff0c;对于关注笔者公众号有一段时间的读者都知道&#xff0c;笔者会每周对自己写过的文章整理至相关专栏&#xff0c;以便读者可以按需进行检索阅读。 你好&#xff0c;我叫sharkchili&#xff0c;目前还是在一线奋斗的Java开…

免费开源的微信小程序源码、小游戏源码精选70套!

微信小程序已经成为我们日常的一部分了&#xff0c;也基本是每个程序员都会涉及的内容&#xff0c;今天给大家分享从网络收集的70个小程序源码。其中这些源码包含&#xff1a;小游戏到商城小程序&#xff0c;再到实用的工具小程序&#xff0c;以及那些令人惊叹的防各大站点的小…

Docker数据卷操作 Docker挂载Nginx、MySQL数据卷

容器与数据&#xff08;容器内文件&#xff09;耦合&#xff1a; 不便于修改&#xff1a;如果需要修改配置文件&#xff0c;需要进入容器的内部。数据不可复用&#xff1a;容器内的修改对外不可见&#xff0c;无法复用。升级维护困难&#xff1a;如果想要升级容器&#xff0c;…

pinia实现todos

store/todos.js //导入defineStore import {defineStore} from pinia const userTodosStoredefineStore(todos,{ state:()>({// list:[// {id:1,name:吃饭,done:false},// {id:2,name:睡觉,done:true},// {id:3,name:打豆豆,done:false}// ],list:JSON.parse(l…

wireshark利用sshdump自身组件进行远程实时抓包过滤

引言 以前在不了解wireshark可以远程抓包的时间&#xff0c;经常通过tcpdump在远程linux主机将抓包文件保存下来后&#xff0c;然后拖拽入windows中再打开&#xff0c;进行分析查看。 此过程比较繁琐&#xff0c;也不够实时。比较常用的抓包动作是仅出现某特征的报文后&#…

六、VTK创建平面vtkPlaneSource

vtkPlaneSource创建位于平面中的四边形数组 先看看效果图: vtkPlaneSource 创建一个 m x n 个四边形数组,这些四边形在平面中排列为规则平铺。通过指定一个原点来定义平面,然后指定另外两个点,这两个点与原点一起定义平面的两个轴。这些轴不必是正交的 - 因此您可以创建平行…

牵手国际企业,OpenAI计划自己制造AI芯片

据外媒报道称&#xff0c;近日&#xff0c;OpenAI的首席执行官萨姆奥特曼正在积极洽谈一项规模达数十亿美元的投资项目&#xff0c;计划与多家顶级芯片制造商合作&#xff0c;建设一个覆盖全球的人工智能芯片生产网络。 奥特曼曾多次反馈目前的芯片已不能满足OpenAI公司的AI研发…

Excel导出指定格式

期望 实现 Slf4j RequestMapping(value "/data") RestController public class DataStatController {GetMapping(value "/export", produces MediaType.APPLICATION_OCTET_STREAM_VALUE)public void export(HttpServletResponse response) {final Stri…

docker 存储管理

文章目录 docker 存储管理容器存储方案docker 容器存储解决方案 docker 存储驱动基本概述存储驱动的选择原则主流的 docker 存储驱动docker 版本支持的存储驱动 overlay2 存储驱动OverlayFSoverlay2 存储驱动要求配置 docker 使用 overlay2 驱动 overlay2 存储驱动的工作机制Ov…

mybatis-plus常用使用方法

** mybaits-plus常用使用方法 ** 常用三层分别继承方法 1.1mapper层&#xff08;接口定义层&#xff09;可以用BaseMapper<> 例如&#xff1a; 1.2.里面常用的封装方法有 1.3常用方法介绍 【添加数据&#xff1a;&#xff08;增&#xff09;】int insert(T entity);…

Neo4j 国内镜像下载与安装

Neo4j 5.x 简体中文版指南 社区版&#xff1a;https://neo4j.com/download-center/#community 链接地址&#xff08;Linux版&#xff09;&#xff1a;https://neo4j.com/artifact.php?nameneo4j-community-3.5.13-unix.tar.gz 链接地址&#xff08;Windows&#xff09;&#x…

uml时序图刻画多个线程的活动

使用box关键字圈入不同线程内的组件 使用loop关键字客刻画线程的定时活动 示例

新建一个基于标准库的工程(STM32)

目录 1.新建存放工程的文件夹 2.打开KEIL5软件 3.新建一个本次工程的文件夹 4.添加工程的必要文件 4.1打开STM32的启动文件 ​编辑 4.2&#xff1a; 4.3添加内核寄存器文件 ​编辑 5.回到keil5软件&#xff0c;将刚才复制的那些文件添加到工程中 5.1添加一个启动文件&am…

vue3+naiveUI二次封装的v-model cascader联级选择框

组件 v-model 源码 <template><div class"clw-cascader pt-3"><n-cascaderref"cascader":value"value":title"title"filterableclearable:check-strategy"checkStrategy":label-field"labelField"…

在 ASP.NET Core Web API 中使用操作筛选器统一处理通用操作

前言&#xff1a;什么是操作筛选器 操作筛选器是 ASP.NET Core Web API 中的一种过滤器&#xff0c;用于在执行控制器操作&#xff08;Action&#xff09;之前或之后执行一些代码&#xff0c;完成特定的功能&#xff0c;比如执行日志记录、身份验证、授权、异常处理等通用的处…

2、鼠标事件、键盘事件、浏览器事件、监听事件、冒泡事件、默认事件、属性操作

一、鼠标事件 1、单击事件&#xff1a;onclick <body><header id"head">我是头部标签</header> </body> <script> var head document.getElementById("head")head.onclick function () {console.log("我是鼠标单击…

Elasticsearch使用经验和云上竞品对比

Elasticsearch使用经验和云上竞品对比 - 知乎 过去三十年&#xff0c;我们从企业应用开始&#xff0c;经历了 PC 互联网、移动互联网的爆发式发展&#xff0c;到如今的产业互联网。在这些不同时代&#xff0c;一直变化的是应用形态&#xff0c;不变的是核心数据的价值。 对于核…

kafka summary

最近整体梳理之前用到的一些东西&#xff0c;回顾Kafka的时候好多东西都忘记了&#xff0c;把一些自己记的比较模糊并且感觉有用的东西整理一遍并且记忆一遍&#xff0c;仅用于记录以备后续回顾 Kafka的哪些场景中使用了零拷贝 生产者发送消息&#xff1a;在 Kafka 生产者发送…

五、Kotlin 函数进阶

1. 高阶函数 1.1 什么是高阶函数 以下 2 点至少满足其一的函数称为高阶函数&#xff1a; 形参列表中包含函数类型的参数 //参数 paramN 可以是&#xff1a;函数引用、函数类型变量、或 Lambda 表达式。 fun funName(param1: Type1, param2: Type2, ... , paramN: (p1: T1, p2…

7.【SpringBoot3】项目部署、属性配置、多环境开发

1. SpringBoot 项目部署 项目完成后&#xff0c;需要部署到服务器上。 SpringBoot 项目需要经过编译打包生成一个 jar 包&#xff08;借助打包插件 spring-boot-maven-plugin&#xff09;&#xff0c;再将该 jar 包发送或拷贝到服务器上&#xff0c;然后就可以通过执行 java …