详解C++ 左值引用与 const 关键字

左值引用是已定义的变量的别名,其主要用途是用作函数的形参,将 const 关键字用于左值引用时,其在初始化时可接受的赋值形式变得更加广泛了,这里来总结一下。

左值引用是已定义的变量的别名,其主要用途是用作函数的形参,通过将左值引用变量用作参数,函数将使用原始数据,而不是副本。引用变量必须在声明时同时初始化,可将 const 关键字用于左值引用,如下所示:

//声明并初始化常规左值引用变量
int x = 55;
int & rx = x;

//将const关键字用于左值引用变量,以下几种为等效表示
int x = 55;
const int & crx = x;
int const & crx = x;

在 Microsoft Visual Studio 中连续多个 const 会被编译器解释成一个,即 const const const const int &const int & 等效,除此之外,const int const & 在 Microsoft Visual Studio 中也与 const int & 等效,而 int & const 在 QT 中将会报错,在 Microsoft Visual Studio 中与 int & 等效。

以上两种类型左值引用的特性如下(旧版 C++ 可能与下列特性不十分吻合,以 C++11 为准):

  • 类型为 int & 的引用 rx 只能作为已有变量的别名,不会生成临时变量,可修改所引用变量的值,可将 int 变量、int & 变量、int * 指针所指变量、int *const 指针所指变量在初始化时赋给 rx(接受可通过地址访问的非 const 变量),必须在声明时初始化,后续无法更换所引用的变量。变量初始化完成后,其表现与 int 类型一致。
  • 类型为 const int & 的引用 crx 既可作为已有变量的别名,也可在合适的时候生成临时变量,成为该临时变量的别名,但不可修改所引用变量的值,可将 int 变量、const int 变量、int & 变量、const int & 变量、int * 指针所指变量、int *const 指针所指变量、const int * 指针所指变量、类型为 int 的非左值(比如字面常量 100、多项表达式 1+50*2、函数的 int 返回值)、类型不是 int 但可转换为 int 的变量或非左值(比如 short 变量、short & 变量、多项表达式 1.0+50.0*2.0、字面常量 100.0、函数的 double 返回值)在初始化时赋给 crx,也必须在声明时初始化,后续无法更换所引用的变量。变量初始化完成后,其表现与 const int 类型一致。

常规左值引用变量的初始化用法如下:

//初始化用法一:作为short变量别名
short x = 55;
short & rx = x;
cout << x;  //结果为55
cout << rx; //结果为55
cout << &x; //32位系统结果为0x0093F7BC
cout << &rx;//32位系统结果为0x0093F7BC
cout << sizeof(x); //结果为2
cout << sizeof(rx);//结果为2

//初始化用法二:作为short变量别名,多层引用
short x = 55;
short & rx = x;
short & rxx = rx;

//初始化用法三:作为short变量别名,指针表示法,指针为short*
short x = 55;
short * px = &x;
short & rx = *px;

//初始化用法四:作为short变量别名,指针表示法,指针为short *const
short x = 55;
short * const px = &x;
short & rx = *px;

const 关键字修饰的左值引用变量初始化用法如下:

//初始化用法一:作为short变量别名
short x = 55;
const short & rx = x;

//初始化用法二:作为const short变量别名
const short x = 55;
const short & rx = x;

//初始化用法三:作为short变量别名,多层引用
short x = 55;
short & rx = x;
const short & rxx = rx;

//初始化用法四:作为short变量别名,多层引用,第一层引用为const
short x = 55;
const short & rx = x;
const short & rxx = rx;

//初始化用法五:作为short变量别名,指针表示法,指针为short*
short x = 55;
short * px = &x;
const short & rx = *px;

//初始化用法六:作为short变量别名,指针表示法,指针为const short*
short x = 55;
const short * px = &x;
const short & rx = *px;

//初始化用法七:作为short变量别名,指针表示法,指针为short *const
short x = 55;
short *const px = &x;
const short & rx = *px;

//初始化用法八:作为short变量别名,指针表示法,指针为const short *const
short x = 55;
const short *const px = &x;
const short & rx = *px;

//初始化用法九:将创建临时变量,类型为int的非左值,字面常量
const int & rx = 100;

//初始化用法十:将创建临时变量,类型为int的非左值,多项表达式
const int & rx = 1+50*2;

//初始化用法十一:将创建临时变量,类型为int的非左值,函数返回int值
const int & rx = abs(10);

//初始化用法十二:将创建临时变量,类型不是int但可转换为int的变量
short x = 55;
const int & rx = x;
cout << x;  //结果为55
cout << rx; //结果为55
cout << &x; //32位系统结果为0x006FFCF0
cout << &rx;//32位系统结果为0x006FFCD8
cout << sizeof(x); //结果为2
cout << sizeof(rx);//结果为4

//初始化用法十三:将创建临时变量,类型不是int但可转换为int的非左值,字面常量
const int & rx = 100.0;

//初始化用法十四:将创建临时变量,类型不是int但可转换为int的非左值,多项表达式
const int & rx = 1.0+50.0*2.0;

将初始化时 int &const int & 可接受的形式列个表,如下:

初始化时可接受的形式 int & 类型 const int & 类型
int 变量 可以 可以
const int 变量 不可以 可以
int & 变量 可以 可以
const int & 变量 不可以 可以
int * 所指变量 可以 可以
int * const 所指变量 可以 可以
const int * 所指变量 不可以 可以
const int * const 所指变量 不可以 可以
形如 100 的 int 字面常量 不可以 可以(将创建临时变量)
形如 1+50*2 的 int 多项表达式 不可以 可以(将创建临时变量)
返回类型为 int 的函数返回值 不可以 可以(将创建临时变量)
类型可以转换为 int 的变量 不可以 可以(将创建临时变量)
形如 100.0 可转换为 int 的字面常量 不可以 可以(将创建临时变量)
形如 1.0+50.0*2.0 可转换为 int 的多项表达式 不可以 可以(将创建临时变量)

到此这篇关于C++ 左值引用与 const 关键字的文章就介绍到这了,更多相关C++ 左值引用const 关键字内容请搜索我们以前的文章或继续浏览下面的相关文章希望大家以后多多支持我们!

(0)

相关推荐

  • C/C++中static,const,inline三种关键字详细总结

    一.关于staticstatic 是C++中很常用的修饰符,它被用来控制变量的存储方式和可见性,下面我将从 static 修饰符的产生原因.作用谈起,全面分析static 修饰符的实质. static 的两大作用: 一.控制存储方式 static被引入以告知编译器,将变量存储在程序的静态存储区而非栈上空间. 引出原因:函数内部定义的变量,在程序执行到它的定义处时,编译器为它在栈上分配空间,大家知道,函数在栈上分配的空间在此函数执行结束时会释放掉,这样就产生了一个问题: 如果想将函数中此变量的值保

  • 一篇文章弄懂C++左值引用和右值引用

    目录 1. 左值和右值 2. 左值引用 3. 右值引用 3.1 出现 3.2 概念 3.3 应用 3.3.1 右值引用绑定到左值上 3.3.2 std::move()本质 3.3.3 移动构造函数和移动赋值运算符 3.3.4 std::move()的一个例子 4. 补充-协助完成返回值优化(RVO) 5. 总结 篇幅较长,算是从0开始介绍的,请耐心看~ 该篇介绍了左值和右值的区别.左值引用的概念.右值引用的概念.std::move()的本质.移动构造函数.移动复制运算符和RVO. 1. 左值和右

  • 浅谈C++左值引用和右值引用

    实例如下: #include<iostream> #include<utility> #include<vector> using namespace std; int f(); int main() { vector<int>vi(100); int i=42; int &&r1=i;//error不能把右值引用绑到左值上 int &&r2=10; int &r3=i; int &r4=10;//error非

  • 详解C++中的const关键字及与C语言中const的区别

    const对象默认为文件的局部变量,与其他变量不同,除非特别说明,在全局作用域的const变量时定义该对象的文件局部变量.此变量只存在于那个文件中中,不能别其他文件访问.要是const变量能在其他文件中访问,必须显示的指定extern(c中也是)   当你只在定义该const常量的文件中使用该常量时,c++不给你的const常量分配空间--这也是c++的一种优化措施,没有必要浪费内存空间来存储一个常量,此时const int c = 0:相当于#define c 0:    当在当前文件之外使用

  • C/C++ 中const关键字的用法小结

    C++中的const关键字的用法非常灵活,而使用const将大大改善程序的健壮性. Const作用 NO. 作用 说明 参考 1 可以定义const常量 const int Max = 100; 2 便于进行类型检查 const常量有数据类型,而宏常量没有数据类型.编译器可以对前者进行类型安全检查,而对后者只进行字符替换,没有类型安全检查,并且在字符替换时可能会产生意料不到的错误 void f(const int i) { ---} //对传入的参数进行类型检查,不匹配进行提示 3 可以保护被修

  • 详解C++ 左值引用与 const 关键字

    左值引用是已定义的变量的别名,其主要用途是用作函数的形参,将 const 关键字用于左值引用时,其在初始化时可接受的赋值形式变得更加广泛了,这里来总结一下. 左值引用是已定义的变量的别名,其主要用途是用作函数的形参,通过将左值引用变量用作参数,函数将使用原始数据,而不是副本.引用变量必须在声明时同时初始化,可将 const 关键字用于左值引用,如下所示: //声明并初始化常规左值引用变量 int x = 55; int & rx = x; //将const关键字用于左值引用变量,以下几种为等效表

  • 详解C++右值引用

    概述 在C++中,常量.变量或表达式一定是左值(lvalue)或右值(rvalue). 左值:非临时的(具名的,可在多条语句中使用,可以被取地址).可以出现在等号的左边或右边.可分为非常量左值和常量左值. 右值:临时的(不具名的,只在当前语句中有效,不能取地址).只能出现在等号的右边.可分为非常量右值和常量右值. 左值引用:对左值的引用就是左值引用.可分为非常量左值引用和常量左值引用. 注:常量左值引用是"万能"的引用类型,可以绑定到所有类型的值,包括非常量左值.常量左值.非常量右值和

  • 详解java的值传递、地址传递、引用传递

    详解java的值传递.地址传递.引用传递 一直来觉得对值传递和地址传递了解的很清楚,刚才在开源中国上看到一篇帖子介绍了java中的值传递和地址传递,看完后感受颇深.下边总结下以便更容易理解. 按照以前的理解,java中基本数据类型是值传递,对象是地址(引用)传递.给大家看个例子: public class ObjectTrans { public static void main(String[] args) { String name = "123"; SChange(name);

  • 详解SpringBoot如何删除引用jar包中的无用bean

    目录 前言 代码示例 实现代码示例 前言 公司有个项目,时间比较赶,而且项目的部分需求,和之前做的项目部分功能一样,为了赶速度和直接将之前多模块的maven项目中的部分模块,直接以jar包的形式引入到新项目中了,虽然省去了不少开发时间,但是造成项目需要导入引入项目jar的相关依赖,导致项目臃肿,启动很慢.有没有办法让项目只加载自己需要的bean呢? 当然我们可以直接修改源代码重新打包引入去解决,但是这个办法太多麻烦. 通过百度的手段,查询可以在springboot启动类上用@ComponentS

  • 实例详解JSON取值(key是中文或者数字)方式

    JSON取值(key是中文或者数字)方式详解 先准备一个json对象用于演示 var json = {'name':'zhangsan', '年龄':23, 404:'你可能迷路了'}; 1.使用JS中with关键字 with(json) { console.log(name);//输出:zhangsan console.log(年龄);//输出:23 console.log(404);//输出:404,用这种方法读取key是数字的属性,有问题 } 2.最常见的传统的读取key console.

  • C++中引用和const关键字介绍

    目录 引用 常引用 const关键字用法 1)定义常量 2)定义常量指针 3)定义常引用 总结 引用 下面的写法定义了一个引用,并将其初始化为引用某个变量.类型名 & 引用名 = 某变量名; int n = 4; int & r = n; // r 引用了n,r的类型是 int & 某个变量的引用,等价于这个变量,相当于该变量的一个别名. int n = 7; int & r = n; // r 引用了n,r和n就是一回事 r = 4; cout << r; /

  • 详解Go语言中new和make关键字的区别

    目录 new 源码 使用 make 源码 使用 总结 本篇文章来介绍一道非常常见的面试题,到底有多常见呢?可能很多面试的开场白就是由此开始的.那就是 new 和 make 这两个内置函数的区别. 其实这个问题本身并不复杂,简单来说就是,new 只分配内存,而 make 只能用于 slice.map 和 chan 的初始化,下面我们就来详细介绍一下. new new 是一个内置函数,它会分配一段内存,并返回指向该内存的指针. 其函数签名如下: 源码 // The new built-in func

  • 详解webpack3如何正确引用并使用jQuery库

    经过百度.谷歌.SF.stackoverflow后终于将webpack3引用jQuery的问题解决了,网上的重复文章太多,大多也都过时了,webpack这两年发展也非常快,大多都是1.0版本的文章,与时俱进的很少,刚刚看了一眼现在已经发展到3.5.5了,真正看其中一篇文章能解决问题的几乎没有,下面是webpack3的实现代码. 首先在配置页面中加入外部引用 externals: { jquery: "jQuery" //如果要全局引用jQuery,不管你的jQuery有没有支持模块化,

随机推荐