问题1:const什么时候为只读变量?什么时候是常量?

const常量的判别准则:

a.只有用字面量初始化的const常量才会进入符号表(直接初始化过的const为常量)

b.被使用其他变量初始化的const常量仍然是只读变量(间接初始化的const为只读变量)

c.被volatile修饰的const常量不会进入符号表(volatile:易变的。每次都要去内存中取出值。所以也是只读变量。voaltile易变的在这里决定了cosnst不可能是一个常量;const则说明在当前的作用域当中,修饰的变量不能出现在赋值符号的左边(只读))

总的来说:在编译期间不能直接确定初始值的const标识符,都被作为只读变量处理

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

类型相同:初始化变量为只读变量

类型不同:生成一个新的只读变量(类型为左值中的类型)

#include <stdio.h>

int main()
{
const int x = 1; //常量
const int& rx = x; //只读变量 int& nrx = const_cast<int&>(rx); nrx = 5; printf("x = %d\n", x); //1 x被写到符号表中
printf("rx = %d\n", rx); //5
printf("nrx = %d\n", nrx); //5
printf("&x = %p\n", &x); //地址相同
printf("&rx = %p\n", &rx);
printf("&nrx = %p\n", &nrx); volatile const int y = 2; //只读变量
int* p = const_cast<int*>(&y); *p = 6; printf("y = %d\n", y); //6
printf("p = %p\n", p); const int z = y; //只读变量 p = const_cast<int*>(&z); *p = 7; printf("z = %d\n", z); //7
printf("p = %p\n", p); char c = 'c';
char& rc = c;
const int& trc = c; //这里const引用的初始化时的类型与初始值类型不同,所以这里被定义成了一个新的只读变量。此时const int& trc = c;相当于给一个名为trc空间的内存赋值了‘c’。 rc = 'a'; //修改不会影响到trc printf("c = %c\n", c);
printf("rc = %c\n", rc);
printf("trc = %c\n", trc); return 0;
}

问题2:引用于指针有什么关系?如何理解“引用的本质就是指针常量”?

指针:

指针是个变量。

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

b.通过指针可以访问对应内存地址中的值

c.指针可以被const修饰成为常量或者只读变量。

引用

引用只是一个变量的新名字。

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

b.const引用使其代表的变量具有只读属性(const修饰的引用是只读变量,但指针还有常量)

c.引用必须在定义时初始化,之后无法代表其他变量。

从使用c++语言的角度来看

a.引用与指针没有任何关系

b.引用是变量的新名字,操作引用就是操作对应的变量

从c++编译器的角度来看

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

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

c.因此“引用”在定义时必须初始化

在工程项目开发中

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

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

思考:下面的代码有问题吗?

int a = 1;
int b = 2;
int *pc = new int(3); //定义一个指针,分配空间并赋值
int& array[] = {a, b, *pc};

测试:

#include <stdio.h>

int a = 1;

struct SV
{
int& x;
int& y;
int& z;
}; int main()
{
int b = 2;
int* pc = new int(3);
SV sv = {a, b, *pc};
int& array[] = {a, b, *pc}; // error &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 0;
}

数组中的每一个元素都是顺序存放的,也就是说他们的地址是递增的。可从测试结果中看到。&array[1] - &array[0] = ? Expected ==> 4。所以c++中不支持引用数组。当然结构体支持(struct SV)。

最新文章

  1. Python学习目录
  2. Python黑帽编程2.2 数值类型
  3. CSS background-color 、image 背景图片
  4. Hello.class所在路径下, 输入命令:java Hello.class,会出现什么结果,为什么?
  5. oracle 10gwindow7安装添加内容
  6. HQL查询语言的使用介绍
  7. JAVA 23种设计模式(转)
  8. 关于 Google Chrome 中的全屏模式和 APP 模式
  9. [Buzz.Today]2013.08.06
  10. C#.NET使用AnimateWindow制作淡入淡出特殊效果的窗体
  11. Java SE ---算术运算符
  12. Swift常量和变量以及命名规范
  13. 第一章 00 StringUtil.cpp和StringUtil.hh分析
  14. code_analyzer(代码分析助手)
  15. Ubuntu apt-get 错误 -11 -system error
  16. myeclipse配置SVN插件
  17. Spark学习笔记2(spark所需环境配置
  18. [Luogu2057]善意的投票
  19. django rest framework ViewSets &amp; Routers
  20. python 删除非空文件夹

热门文章

  1. CCPC 2017 哈尔滨 L. Color a Tree &amp;&amp; HDU 6241(二分+树形DP)
  2. Qt 程序自动重启的实现
  3. 智能指针weak_ptr记录
  4. nginx常用命令和配置
  5. Luogu P2602 [ZJOI2010]数字计数 数位DP
  6. prevAll([expr]) 查找当前元素之前所有的同辈元素
  7. ajax+批量下载文件
  8. jQuery的$符号
  9. leetcode题目234.回文链表(快慢指针+辅助空间-简单)
  10. Linux设备驱动程序 之 完成量