C++ 学习之旅(8)——一文搞懂指针、引用、函数参数的传值调用、指针调用和引用调用
废话少说,直接上代码:
#include <iostream>int main()
{int a = 5;int* ptr = &a;int& ref = a;std::cin.get(); //设置断点
}
为了避免混淆,我建议在定义指针时写int* ptr
而不是int *ptr
,同理,定义引用写成int& ref
而不是int &ref
。
设置断点,然后Debug程序,看看源程序的汇编程序是什么:
精彩的地方来了,指针和引用实际上干的是同样的事,都是把变量a所在的偏移地址传给ptr指针,只不过指针的标号名为ptr,引用的标号名为ref而已。
再看看赋值操作:
#include <iostream>int main()
{int a = 5;int* ptr = &a;int& ref = a;*ptr = 6; //赋值ref = 7; //赋值std::cin.get();
}
在汇编语言中还是一样的!
最后看一下函数参数传递的三种方式:
#include <iostream>void Increment1(int value) //传值
{value++;
}void Increment2(int* value) //指针
{(*value)++;
}void Increment3(int& value) //引用
{value++;
}int main()
{int a = 5;Increment1(a);Increment2(&a);Increment3(a);std::cin.get();
}
Increment1函数
Increment2函数
Increment3函数
可以看到指针和引用还是一样的,结合调用的代码看:
首先,把5送到内存地址为a的双字大小的空间中;
对于Increment1,从内存地址为a的双字大小的空间中取出内容(整数5),送到eax寄存器中,然后call函数Increment1,把eax加一,最后送到内存地址为value的空间中,而不是内存地址为a的空间,如图:
对于Increment2,取内存地址为a的偏移地址,送到eax寄存器中,然后call函数Increment2,如图:
先是寻址参数value,从中取出偏移地址送到eax,再用eax寻址,找到数值5送到ecx,然后ecx加一,再将结果ecx送回到偏移地址为value空间中记录的那个地址,即内存地址a,这样就实现了对a的加一操作。
顺便看下此时的value空间,记录的是内存地址a的偏移地址:
也就是说,如果使用传值调用,内存地址为参数value的空间中记录的就是数值,运算的结果也会记录在这里,但是如果函数退出,这一块空间就会清除,所以结果并没有保存。如果使用指针和引用调用,内存地址为参数value的空间中记录的就是偏移地址,然后根据这个偏移地址取值,作运算,结果也是根据这个偏移地址送回去,而这块空间即使函数退出也不会消失。
C++ 学习之旅(8)——一文搞懂指针、引用、函数参数的传值调用、指针调用和引用调用相关推荐
- [深度学习] Attention机制,一文搞懂从实例到原理
一 人类的视觉注意力 扩展阅读: Attention and Augmented Recurrent Neural Networks[译文] 不用看数学公式!图解谷歌神经机器翻译核心部分:注意力机制 ...
- 一文搞懂C++虚函数的实现原理
虚函数的概念 虚函数是实现C++中面向对象的三大特性之一--多态的一种技术手段. 什么是多态呢? 在基类的成员函数前,使用virtual修饰得到的就是虚函数.在派生类中,对继承得到的虚函数,进行重写, ...
- 一文搞懂如何使用ArcGIS API for Python训练深度学习模型
一文搞懂如何使用ArcGIS API for Python训练深度学习模型 文章目录 一文搞懂如何使用ArcGIS API for Python训练深度学习模型 写在前面 一.ArcGIS API f ...
- 一文搞懂UART通信协议
目录 1.UART简介 2.UART特性 3.UART协议帧 3.1.起始位 3.2.数据位 3.3.奇偶校验位 3.4.停止位 4.UART通信步骤 1.UART简介 UART(Universal ...
- 一文搞懂I2S通信总线
目录 1.物理特性 2.常见的I2S数据格式 2.1.I2S Philips标准 2.2.左对齐(MSB)标准 2.3.右对齐(LSB)标准 之前我们讲过I2C通信总线,本篇博文将讲一讲I2C的变种: ...
- ES6学习——一文搞懂ES6
ES6学习--一文搞懂ES6 es6介绍 ES全称EcmaScript,是脚本语言的规范,而平时经常编写的EcmaScript的一种实现,所以ES新特性其实就是指JavaScript的新特性. 为什么 ...
- 一文搞懂RNN(循环神经网络)
基础篇|一文搞懂RNN(循环神经网络) https://mp.weixin.qq.com/s/va1gmavl2ZESgnM7biORQg 神经网络基础 神经网络可以当做是能够拟合任意函数的黑盒子,只 ...
- 一文搞懂 Python 的 import 机制
一.前言 希望能够让读者一文搞懂 Python 的 import 机制 1.什么是 import 机制? 通常来讲,在一段 Python 代码中去执行引用另一个模块中的代码,就需要使用 Python ...
- 【UE·蓝图底层篇】一文搞懂NativeClass、GeneratedClass、BlueprintClass、ParentClass
本文将对蓝图类UBlueprint的几个UClass成员变量NativeClass.GeneratedClass.BlueprintClass.ParentClass进行比较深入的讲解,看完之后对蓝图 ...
- 一文搞懂AWS EC2, IGW, RT, NAT, SG 基础篇下
B站实操视频更新 跟着拉面学习AWS--EC2, IGW, RT, NAT, SG 简介 长文多图预警,看结论可以直接拖到"总结"部分 本文承接上一篇文章介绍以下 AWS 基础概念 ...
最新文章
- Caffe源码中math_functions文件分析
- 通知 | 2020年度“RONG”奖学金入围答辩名单公布
- 【Android Gradle 插件】ProductFlavor 配置 ( ProductFlavor#manifestPlaceholders 清单文件占位符配置 )
- docker tensorflow-jupyter简单使用
- 使用Intent来启动Activity并传递参数
- windows10大瘦身 - Lync录屏的临时文件夹清理
- ubuntu 报错E: Unable To Locate Package Software-properties-common
- python3+xlrd解析Excel
- jenkind + git + mave + shell + tomcat
- 字节跳动面试题 问题定位
- Spring之Bean后处理器——BeanPostProcessor的使用与源码解析
- 配色表 色卡 前段色彩
- python如何控制手机发短信_利用Python实现手机短信监控通知
- 已知ip地址和其子网掩码如何求网络号子网号主机号
- MAC OS升级记录
- jzoj 6012.【NOIP2019模拟1.25A组】荷马史诗 dp
- windows防火墙开启后,设置准入端口
- 2017 ACM Arabella Collegiate Programming Contest A. Sherlock Bones GYM101350A
- Linux打tar包命令
- 关于Form表单的提交与验证???
热门文章
- 六台机器搭建RedisCluster分布式集群
- oracle optimizer_features_enable,Oracle Optimizer:迁移到使用基于成本的优化器—–系列2.1-数据库专栏,ORACLE...
- 数学的意蕴与价值(建议收藏)
- linux c之通过popen执行shell命令
- Struts2的ResultType和Action处理链
- 《假如编程是魔法之零基础看得懂的Python入门教程 》——(一)既然你选择了这系列教程那么我就要让你听得懂
- python桌面程序开发_程序员之路:python3+PyQt5+pycharm桌面GUI开发
- 安卓设备刷linux发行版,绝对精华,大牛教你在Android系统上安装linux发行版
- ​“北斗女神”徐颖,32岁成为中科院最年轻的博导!
- 颜宁分享干货:给实验室博士的一些忠告