详谈c++的引用

引用

引用不是定义一个新的变量,而是给已经定义了的变量起一个别名。一旦把引用初始化为某个变量,就可以使用该引用名称或变量名称来指向变量。

  • 定义的格式为:
    类型&引用变量名=已定义过的变量名
  • 引用的特点
    》 一个变量可取多个别名
    》 引用必须初始化
    》引用只能在初始化的时候引用一次,不能改变为再引用其他的变量

这里写图片描述
这里的a和b是同一块空间的名字。

  • const引用
    我们都知道,当cost修饰变量时,所修饰的变量在之后的使用中是不能被改变的,当const修饰引用是,也遵循这个原则。

这里写图片描述

引用做参数
 void Swap (int& left, int& right)
{
int temp = left;
right = left ;
left = temp ;
}
void test()
{
    int a = 10;
    int b = 20;
    swap(a, b)
    cout << "a:" << a << endl;
    cout << "b:" << b << endl;
}

上面的代码是我们熟知的交换函数,注意left 和right分别 是a和b的别名,通过引用传递,不用定义新的变量,就可以根据别名直接找到a和b这两个数的地址。有没有感觉与指针传递很类似呢!注意:形参是实参的一份临时拷贝,但是引用传递并没有给形参重新分配空间奥(牢记引用的概念)。当不希望函数内改变参数x的值时,尽量使用常引用传参

注意:
C++ 函数传参:

(1)将变量名作为实参和形参。这时传给形参的是变量的值,传递是单向的。如果在执行函数期间形参的值发生变化,并不传回给实参。因为在调用函数时,形参和实参不是同一个存储单元。// 同 c

(2) 传递变量的指针。形参是指针变量,实参是一个变量的地址,调用函数时,形参(指针变量)指向实参变量单元。这种通过形参指针可以改变实参的值。// 同 c

(3) C++提供了 传递变量的引用。形参是引用变量,和实参是一个变量,调用函数时,形参(引用变量)指向实参变量单元。这种通过形参引用可以改变实参的值。

引用做返回值
int arr[] = { 1, 2, 3, 4, 5 };
int& print_num(int i)
{
    return arr[i];
}

int main()
{
    //改变前
    for (int i = 0; i < 5; i++)
    {
        cout << arr[i];
    }
    printf("\n");

    print_num(2) = 0;
    print_num(3) = 0;
    //改变后
    for (int i = 0; i < 5; i++)
    {
        cout << arr[i];
    }
    printf("\n");
    system("pause");
    return 0;
}

执行结果:
这里写图片描述
所以返回一个局部变量的引用是非常危险的。

用汇编详细看一下

这里写图片描述

传值返回时,是将ret的值放入eax寄存器中。**
传引用返回时,是将ret的地址放入eax寄存器中**

当引用作为返回值,必须遵守以下规则:
(1)不能返回局部变量的引用。主要原因是局部变量会在函数返回后被销毁,因此被返回的引用就成为了”无所指”的引用,程序会进入未知状态。
(2)不能返回函数内部new分配的内存的引用。虽然不存在局部变量的被动销毁问题,可对于这种情况(返回函数内部new分配内存的引用),又面临其它尴尬局面。例如,被函数返回的引用只是作为一 个临时变量出现,而没有被赋予一个实际的变量,那么这个引用所指向的空间(由new分配)就无法释放,造成memory leak。
(3)可以返回类成员的引用,但最好是const。主要原因是当对象的属性是与某种业务规则(business rule)相关联的时候,其赋值常常与某些其它属性或者对象的状态有关,因此有必要将赋值操作封装在一个业务规则当中。如果其它对象可以获得该属性的非常 量引用(或指针),那么对该属性的单纯赋值就会破坏业务规则的完整性。

引用与指针的区别
  1. 引用只能在定义时初始化一次,之后不能改变指向其它变量(从一而终);指针变量的值可变。
  2. 引用必须指向有效的变量,指针可以为空。
  3. sizeof指针对象和引用对象的意义不一样。sizeof引用得到的是所指向的变量的大小,而sizeof指针是对象地址的大小。
  4. 指针和引用自增(++)自减(–)意义不一样。
  5. 相对而言,引用比指针更安全。

猜你喜欢

转载自blog.csdn.net/ddcodingya/article/details/79672229