C++的引用和指针的区别?
- 引用是一种更安全的指针。
- 引用是必须初始化的,并且初始化的值是一定要可以取地址的。但是指针可以不初始化。
- 引用只有一级引用,没有多级引用;但是指针可以有一级指针,也可以有多级指针
- 定义一个引用变量,和定义一个指针变量,其汇编指令是一模一样的;通过引用变量修改所引用内存的值,和通过指针解引用修改指针指向的内存的值,其底层指令也是一模一样的
我们编译运行上面代码:
- a,*p,b是属于同一块内存的。
- 引用是别名,a的另一个名字是b,代表的都是同一块内存。
看看汇编指令:
- 定义一个指针变量和定义一个引用变量在汇编上是一模一样的。
- lea是移动地址,把a的地址放到eax寄存器中,move是移动值,然后把eax的值放到p的4字节内存里面。
看看通过指针解引用和引用进行修改值:
- 把p指向的4字节地址放到eax寄存器,然后把14h放到eax存储的4字节的内存里面。
- 底层指令都是通过指针 *** 作的方式进行的。
定义一个引用变量,也是要先把引用的内存地址存储下来,通过引用变量赋值的时候也是要先从底层拿到引用的内存地址,然后通过地址解引用的 *** 作来修改所引用的内存的值,和指针是一样的。
引用要求:
- 需要初始化;
- 要求初始化的值一定能够取地址;
这个是错误的。因为20是无法取地址的。
我们看下面例子swap:
用指针的方式:
用引用的方式:
汇编的层面,引用的底层就是转换成指针实现的。
指针在32位系统都是4字节大小。array是整个数组的大小,所以打印出来是4*5=20个字节大小。
再看看引用变量:
现在打印sizeof(q)就是在打印sizeof(array),也是20的大小。
array和q是一回事了。
左值和右值使用引用变量的时候,总是会做一个解引用 *** 作,从底层把它所引用内存的地址拿出来,然后做一个解引用。
右值是不能引用的。
C++11以后提供了右值引用
我们看看底层汇编指令:
左值引用:
右值引用:
把14h放到栈上的生成的临时量内存里,然后把临时量内存的地址放到寄存器里面,然后把这个地址放到底层的c的指针变量里面。
下面两个是一样的,底层汇编的指令是一模一样的。
先产生临时量,把20存起来,然后把临时量的地址放在寄存器里,最后把地址存放到定义引用变量底层的指针上。
区别:
- d不能修改了,因为被const修饰了,
- 但是这个&&c可以修改临时量的内存。
右值引用变量,本身还是一个左值!
右值引用在生成指令时,必须生成临时量,然后直接引用临时量。
1.int &&c = 20; 专门用来引用右值类型,指令上,可以自动产生临时量
然后直接引用临时量 c = 40;
2.右值引用变量本身是一个左值,只能用左值引用来引用它
3.不能用一个右值引用变量,来引用一个左值
欢迎分享,转载请注明来源:内存溢出
评论列表(0条)