C++“引用”的理解

普通引用

变量名实质上是一段连续存储空间的别名,是一个标号(门牌号) 。
程序中通过变量来申请并命名内存空间,通过变量的名字可以使用存储空间。
问题:对一段连续的内存空间只能取一个别名吗?

引用的概念

引用可以理解为已定义变量的别名

语法:Type& name = var;
例如:

int main 
{
    int a = 10;
    int &b = a;
    b = 20;

    cout << a << endl;
}

输出结果:20

引用做函数参数

#include <iostream>
using namespace std;

struct Teacher
{
    char name[20];
    int age;
};

void printTec1(Teacher *);
void printTec2(Teacher &);
void printTec3(Teacher);

void printTec1(Teacher * pt)
{
    cout << "printTec1 : " << pt->age << endl;
    pt->age = 30;
}

void printTec2(Teacher &pt)
{
    cout << "printTec2 : " << pt.age << endl;
    pt.age = 40;
}

void printTec3(Teacher pt)
{
    cout << "printTec3 : " << pt.age << endl;
    pt.age = 50;
}

void main() {
    Teacher t1;
    t1.age = 20;

    printTec1(&t1);// t1的地址赋值给形参指针变量pt
    cout << "after printTec1 : " << t1.age << endl;
    printTec2(t1);// pt是t1的别名,操作pt相当于直接操作t1
    cout << "after printTec2 : " << t1.age << endl;
    printTec3(t1);// pt是形参,t1拷贝一份数组给了pt,相当于pt=t1;修改pt不影响t1
    cout << "after printTec3 : " << t1.age << endl;

    cin.get();
}

结果:
这里写图片描述

引用做函数返回值

#include <iostream>

using namespace std;

int& fun1();
int& fun2();

int& fun1()
{
    int a = 10;
    return a;// 返回栈变量a
}

int& fun2()
{
    static int a = 20;
    return a;// 返回静态变量a
}

void main() {

    int a = fun1(); // 使用普通变量来接,接的是a的值,没有问题
    int &b = fun1();// 使用引用变量来接,接的是a的地址,a的地址已经被回收
    int &c = fun2();

    cout << "a = " << a << endl;
    cout << "b = " << b << endl;
    cout << "c = " << c << endl;

    cin.get();
}

当函数返回值为引用时
1、若返回栈变量:不能成为其它引用的初始值,不能作为左值使用。
2、若返回静态变量或全局变量:可以成为其他引用的初始值,可作为左值使用。

指针的引用

#include <iostream>

using namespace std;

struct Teacher
{
    char name[20];
    int age;
};

void getTeacher(Teacher **tr)
{
    Teacher *tmp = NULL;
    tmp = (Teacher *)malloc(sizeof(Teacher));
    tmp->age = 27;
    *tr = tmp;
}

void getTeacher2(Teacher * &tr)
{
    tr = (Teacher *)malloc(sizeof(Teacher));
    tr->age = 29;
}

void main() {

    Teacher *pt = NULL;
    getTeacher(&pt);// 通过二级指针,间接改pt赋值
    cout << pt->age << endl;
    delete pt;


    Teacher *pt2 = NULL;
    getTeacher2(pt2);// 通过引用,直接修改pt2
    cout << pt2->age << endl;
    delete pt2;

    cin.get();
}

这里写图片描述

引用的意义

1、引用作为其它变量的别名而存在,因此在一些场合可以代替指针
2、引用相对于指针来说具有更好的可读性和实用性
3、对比间接赋值成立的三个条件:①定义两个变量(实参、形参)、②建立关联(实参取地址传给形参)、③*形参间接修改实参的值。引用在实现上,只不过是帮我们完成了第②步,简化了第③步,将②③合二为一。

这里写图片描述

引用本质思考

定义引用时必须初始化,类似常量,一旦与某个变量关联起来,就将一直效忠于它。

这里写图片描述

引用所占用的空间大小与指针相同。

这里写图片描述

总结:
1、引用在C++中的内部实现是一个常指针,换句话说,引用在C++中是
下述代码的伪装表示:

Type &name <——>Type * const name

2、C++编译器在编译过程中使用常指针作为引用的内部实现,因此引用所占用的空间大小与指针相同。
3、从使用的角度,引用会让人误会其只是一个别名,没有自己的存储空间。这是C++为了实用性而做出的细节隐藏。

何时使用引用

这里写图片描述

常量引用

常量引用两种初始化方式:
1、用变量初始化

int x = 20;
const int &y = x;

2、用字面量初始化

cont int &c = 30;
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值