1,关于 const 的疑问:

1,const 什么时候为只读变量,什么时候是常量;

1,const 从 C 到 C++ 进化的过程中得到了升级,const 在 C++ 中不仅仅像在 C 中声明一个只读变量,其在 C++ 中完全可以得到一个常量;

2,const 常量的判别准则:

1,只有用字面量初始化的 const 常量才会进入符号表;

1,这里是字面量初始化 const 常量,不是 const 常引用;

2,得到了真正意义上的常量;

2,使用其他变量初始化的 const 常量仍然是只读变量;

1,编译器在编译期间不可能知道变量初始化时候的值;

2,得到只读变量;

3,被 volatile 修饰的 const 常量不会进入符号表;

1,volatile 表示声明的标识符是易变的;

2,这个可能的易变性也许不在当前编译的文件中,发生在外部;

3,外部相当于在其它文件中,比如多线程、中断等;

4,每次访问 volatile 修饰的标识符时,因为是易变的,所以应该到内存中直接读取;

5,意味着被 volatile 修饰的标识符不可能进入符号表;

6,意味着当 volatile 和 const 同时修饰一个标识符时,得到的是只读变量,不可能进入符号表;

7,const 此时的意义说明在当前的文件或者当前的作用域当中,volatile 和 const 一起修饰的标识符不能出现在赋值符号的左边;

(4),在编译期间不能直接确定初始值的 const 标识符,都被作为只读变量处理;

3,const 引用的类型与初始化变量的类型:

1,相同:初始化变量成为只读变量;

2,不同:生成一个新的只读变量;

4,const 典型问题分析编程实验:

1,main.cpp 文件:

 #include <stdio.h>

 int main()
{
const int x = ;//直接得到值,进入符号表,但是还是会为 x 分配空间,只不过这个空间 x 没有用而已;
const int& rx = x;//rx代表只读变量,这个变量是编译器为x分配而没有使用的空间;引用代表变量的别名,而变量代表一段内存空间的别名,所以引用代表一段内存空间的别名; int& nrx = const_cast<int&>(rx); //消除 rx只读属性,和rx 代表的内存空间相同; nrx = ; printf("x = %d\n", x);
printf("rx = %d\n", rx);
printf("nrx = %d\n", nrx);
printf("&x = %p\n", &x);
printf("&rx = %p\n", &rx);
printf("&nrx = %p\n", &nrx); volatile const int y = ; // 只读变量;
int* p = const_cast<int*>(&y); //y被 const修饰,取到的地址也有 const 属性,这里将地址只读属性去掉; *p = ; printf("y = %d\n", y);
printf("p = %p\n", p); const int z = y; // y 是变量,得到只读变量; p = const_cast<int*>(&z); *p = ; printf("z = %d\n", z);
printf("p = %p\n", p); char c = 'c';
char& rc = c;
const int& trc = c; // char 类型默认转换为 int;const 引用初始化类型不同,将得到新的只读变量,所以改变 rc 和 trc 没有丝毫关系; rc = 'a'; printf("c = %c\n", c);
printf("rc = %c\n", rc);
printf("trc = %c\n", trc);
printf("&c = %p\n", &c);
printf("&rc = %p\n", &rc);
printf("&trc = %p\n", &trc); return ;
}

2,输出结果:

 x =   // 进入符号表,编译期间就是 1;
rx =
nrx =
&x = 0xbfb1a708//为const修饰的标识符分配空间,通过指针或引用使用;
&rx = 0xbfb1a708
&nrx = 0xbfb1a708
y =
p = 0xbfb1a6fc
z =
p = 0xbfb1a6f4
c = a
rc = a
trc = c // 原始的赋值结果;
&c = 0xbfd1242f
&rc = 0xbfd1242f
&trc = 0xbfd12408 // 新开辟的空间;

5,关于引用的疑问:

1,引用与指针有什么关系,如何理解“引用的本质就是指针常量”;

6,指针和引用分析:

1,指针是一个变量:

1,值为一个内存地址,不需要初始化,可以保存不同的地址;

2,通过指针可以访问对应内存地址中的值;

3,指针可以被 const 修饰成为常量或者只读变量;

2,引用只是一个变量的新名字:

1,对引用的操作(赋值,取地址等)都会传递到代表的变量上;

1,新名字是一段内存空间的代号;

2,引用是给已经存在的合法内存空间一个新的代号;

2,const 引用使其代表的变量具有只读属性;

3,引用必须在定义时初始化,之后无法代表其它变量;

1,身份证号代表一个人,不能复用;

2,一个车牌号就代表一个车,不能复用;

3,因为是指针常量,所以不能代表其它变量;

7,从 C++ 不同角度分析引用:

1,从使用 C++ 语言的角度来看:

1,引用与指针没有任何的关系;

2,引用是变量的新名字,操作引用就是操作对应的变量;

2,从 C++ 编译器的角度来看:

1,为了支持新概念,“引用”必须要一个有效的解决方案;

2,在编译器内部,使用指针常量来实现“引用”;

3,因此“引用”在定义时必须初始化;

8,在工程项目开发中:

1,当进行 C++ 编程时,直接站在使用的角度看待引用,与指针毫无关系,引用就是变量的别名;

2,当对 C++ 代码进行调试分析时,一些特殊情况,可以考虑站在 C++ 编译器角度看待引用;

3,下面代码正确吗?

 int a = ;
int b = ;
int* pc = new int();
int& array[] = [a, b, *pc];

9,引用典型问题分析编程实验:

1,main.cpp 文件:

 #include <stdio.h>

 int a = ;

 struct SV
{
int& x;
int& y;
int& z;
}; int main()
{
int b = ;
int* pc = new int();
SV sv = {a, b, *pc}; // 结构体中的每个元素是引用就可以;
// int& array[] = {a, b, *pc}; //数组中的每个元素是引用就不可以;error: declaration of ‘array’ as array of references; C++ 天生要支持 C 语言,C 语言中数组中的每个元素在内存中是顺序存放的,地址是递增的,所以在 C++ 中也要兼容这个特性,而在 C++ 中唯有引用数组破快了这个特性,所以说 C++ 中不支持引用数组;&array[1] - &array[0] = ? Expected ==> 4; printf("&sv.x = %p\n", &sv.x);
printf("&sv.y = %p\n", &sv.y);
printf("&sv.z = %p\n", &sv.z); delete pc; return ;
}

2,输出结果:

&sv.x = 0x804a020

   &sv.y = 0xbffe92bc

   &sv.z = 0x9f97008

3,在开发中遇到奇怪的 bug,要站在编译器的角度考虑问题;

10,小结:

1,指针是一个变量;

2,引用是一个变量的新名字;

3,const 引用能够生成新的只读变量;

4,在编译器内部使用指针常量实现“引用”;

1,C++ 中为了兼容 C 语言中的所有特性,放弃了引用数组,这样会使得相邻元素的地址之差不是期望的;

5,编译时不能直接确定初始值的 const 标识符都是只读变量;

C++ 中的 const、引用和指针的深入分析的更多相关文章

  1. c++中的引用与指针的区别

    http://blog.csdn.net/lyd_253261362/article/details/4323691 c++中的引用与指针的区别 ★ 相同点: 1. 都是地址的概念: 指针指向一块内存 ...

  2. 不可或缺 Windows Native (18) - C++: this 指针, 对象数组, 对象和指针, const 对象, const 指针和指向 const 对象的指针, const 对象的引用

    [源码下载] 不可或缺 Windows Native (18) - C++: this 指针, 对象数组, 对象和指针, const 对象,  const 指针和指向 const 对象的指针, con ...

  3. C++中引用与指针的区别(详细介绍)

    C++中引用与指针的区别(详细介绍) C++中的引用与指针的区别   指向不同类型的指针的区别在于指针类型可以知道编译器解释某个特定地址(指针指向的地址)中的内存内容及大小,而void*指针则只表示一 ...

  4. C++ 中引用与指针的区别

    1.引用只是变量的一个别名,并不占用内存空间,而指针是一个变量,里面保存着被指向的变量在内存中的地址: 2 引用只能在定义时被初始化一次,之后不可变,而指针可变: 3 引用没有 const,指针有 c ...

  5. [ZZ]C++中,引用和指针的区别

    (1) 引用总是指向一个对象,没有所谓的 null reference .所有当有可能指向一个对象也由可能不指向对象则必须使用 指针. 由于C++ 要求 reference 总是指向一个对象所以 re ...

  6. 基类中定义的虚函数在派生类中重新定义时,其函数原型,包括返回类型、函数名、参数个数、参数类型及参数的先后顺序,都必须与基类中的原型完全相同 but------> 可以返回派生类对象的引用或指针

      您查询的关键词是:c++primer习题15.25 以下是该网页在北京时间 2016年07月15日 02:57:08 的快照: 如果打开速度慢,可以尝试快速版:如果想更新或删除快照,可以投诉快照. ...

  7. c++中的const参数,const变量,const指针,const对象,以及const成员函数

    const 是constant 的缩写,“恒定不变”的意思.被const 修饰的东西都受到强制保护,可以预防意外的变动,能提高程序的健壮性.所以很多C++程序设计书籍建议:“Use const whe ...

  8. C、C++中引用与指针的区别

    1:引用的和指针在概念上的区别 引用是变量的别名,例如 int m; int &n=m; 引用作为一个别名.它在逻辑上不是独立的,它的存在具有依附性,所以引用必须在一开始就被初始化,而且其引用 ...

  9. 【C++】C++中的引用与指针

    想必大家对C++中的指针都有所了解,但是什么是引用呢?C++11标准引入了“引用”的新功能. 引用 引用(reference):给对象起了另外一个名字,引用类型引用(refers to)另外一种类型, ...

随机推荐

  1. fputc, fputs, putc, putchar, puts - 输出字符和字符串

    总览 (SYNOPSIS) #include <stdio.h> int fputc(int c, FILE *stream); int fputs(const char *s, FILE ...

  2. smbmount - 装载一个 smbfs 文件系统

    总览 SYNOPSIS smbmount {service} {mount-point} [-o options] 描述 DESCRIPTION smbmount 可以装载一个Linux SMB文件系 ...

  3. Android listview子控件的的点击事件(转)

    1.先看图,是否是你想要的 2.布局文件<?xml version="1.0" encoding="utf-8"?><LinearLayout ...

  4. ZYNQ的Linux Linaro系统镜像制作SD卡启动(仅使用mkfs部分,其他部分待看)

    0. 概述 ZYNQ生成uboot的时候和正常的ARM设备不太一样,ZYNQ属于二次辅助启动uboot然后由uboot启动内核,大概意思就是 ZYNQ内部有一个机制,该机制不可修改,可以通过拨码开关控 ...

  5. Linux centos7安装git

    1.下载git wget https://github.com/git/git/archive/v2.14.1.zip 2.安装依赖 yum -y install zlib-devel openssl ...

  6. Codeforces Round #584 - Dasha Code Championship - Elimination Round (rated, open for everyone, Div. 1 + Div. 2)

    怎么老是垫底啊. 不高兴. 似乎 A 掉一道题总比别人慢一些. A. Paint the Numbers 贪心,从小到大枚举,如果没有被涂色,就新增一个颜色把自己和倍数都涂上. #include< ...

  7. 51nod 1714:B君的游戏(博弈 sg打表)

    题目链接:https://www.51nod.com/onlineJudge/questionCode.html#!problemId=1714 nim游戏的一个变形,需要打出sg函数的表 #incl ...

  8. 【leetcode】659. Split Array into Consecutive Subsequences

    题目如下: 解题思路:本题可以维护三个字典,dic_1保存没有组成序列的单元素,dic_2保存组成了包含两个元素的序列中的较大的元素,dic_3保存组成了包括三个或者三个以上元素的序列中的最大值.因为 ...

  9. Java Web学习总结(2)Servlet(一)

    一,Servlet 简介 Java Servlet 是运行在 Web 服务器或应用服务器上的程序,它是作为来自 Web 浏览器或其他 HTTP 客户端的请求和 HTTP 服务器上的数据库或应用程序之间 ...

  10. STM32输入捕获TIM2四通道

    相比于一通道,原子的例程里因为清了计数时间,所以要对程序进行修改. 记录上升沿后的计数,然后记录下降沿的计数.相减后计算高电平时间,对于定时器中断间隔的边界要分开处理. 这里因为我的接收机时间是1ms ...