文档章节

C++左值右值傻傻分不清楚

LoSingSang
 LoSingSang
发布于 01/11 16:47
字数 643
阅读 7
收藏 0
F2

关键字:左值、右值、std::move()、std::forward<T>()、模板类型推断、转发

----------------------------------------------------------------------------------------------------------------

1

当一个对象被用作右值的时候,用的是对象的值(内容);当对象被用作左值得时候,用的是对象的身份(在内存中的位置)。

对于一个左值,只能用左值引用。(1)
对于一个右值,可以用右值引用(5),或者用const左值引用(3)。
以上,左值可以替代右值使用(因为可以const左值引用绑定到右值上),但是右值不能被当作左值使用

//i是一个左值,1是右值
int i = 1;

//1.左值引用绑定到上,即r是i的别名
int &r = i;//正确

//2.不能将左值引用绑定到右值上,i * 42是右值
int &r2 = i * 42;//错误
//3.但是可以将const的左值引用绑定到右值上
const int &r2 = i * 42;//正确

//4.不能将右值引用绑定到左值上
int &&r3 = i;//错误
//5.将右值引用绑定到右值上
int &&r3 = i * 42;//正确

----------------------------------------------------------------------------------------------------------------

2

part1说到
对于一个左值,只能用左值引用。
为了使右值引用绑定到左值上,引入了std::move(左值)

对于part1的(4)写成:
int &&r3 = std::move(i);//正确
当使用了std::move(i),就相当于承诺除了对i赋值或销毁外,不再使用i!

----------------------------------------------------------------------------------------------------------------

3

通过part1也能说明
对于
template <typename T> void f1(T&)//实参必须是左值
f1(i);//正确
f1(1);//错误

template <typename T> void f2(const T&)//实参可接受右值,也可接受右值,因为const左值引用可以绑定到右值上
f1(i);//正确
f1(1);//正确

对于
template <typename T> void f3(const T&&)//实参可接受右值,也可接受右值,通常通过std::forward<T>()实现完美转发
f1(i);//正确,推断T的类型为int&
f1(1);//正确,推断T的类型为int
当向右值引用函数参数传递右值时,有实参推断出的类型为该右值的类型

----------------------------------------------------------------------------------------------------------------

4

完美转发

void processValue(int& a){ cout << "lvalue" << endl; }
void processValue(int&& a){ cout << "rvalue" << endl; }

template <typename T>
void forwardValue(T&& val)
{
    processValue(std::forward<T>(val)); //照参数本来的类型进行转发。
}
void Testdelcl()
{
    int i = 0;
    forwardValue(i); //传入左值 
    forwardValue(0);//传入右值 
}

输出:
lvaue 
rvalue

参考:https://www.cnblogs.com/qicosmos/p/4283455.html

----------------------------------------------------------------------------------------------------------------

5

std::move()
std::forward<T>()

头文件<utility>
带上std,避免名字空间冲突

 

以上 

© 著作权归作者所有

共有 人打赏支持
LoSingSang
粉丝 3
博文 53
码字总数 16173
作品 0
深圳
程序员
私信 提问
MySQL join left join right join 区别

MySQL join left join right join 区别 前提准备条件 join 指User和Book中都存在的关联关系的结果 left Join 左连接查询,根据字面意思可以理解,主要返回左表中的信息,如果...

superduper
2017/10/19
0
0
C++ 0x 之左值与右值、右值引用、移动语义、传导模板

左值与右值 左值与右值的概念要追溯到 C 语言,由 C++ 语言继承了上来。C++ 03 3.10/1 如是说:“Every expression is either an lvalue or an rvalue.”左值与右值是指表达式的属性,而非对...

雅各宾
2013/11/27
0
2
C++:一段代码,了解拷贝构造函数、move构造函数、拷贝赋值函数、move赋值函数、右值引用

本文纯粹是个整理。 以下代码和图片来自C++ 11右值引用。 其他: 什么是左值、右值: C++左值与右值之道 C++左值与右值之间共同与不同点解析 C/C++左值性精髓(一) 左值的前世今生 C/C++左值...

樂天
2015/06/25
0
0
C/C++左值性精髓(二)哪些表达式是左值,哪些是右值?----后缀表达式

在表达式的左值性中,后缀表达式是比较复杂的一种情况。后缀表达式有很多种,这里讨论的是E1.E2和E1->E2形式的后缀表达式。 4.1 E1.E2形式的后缀表达式 若E2为静态数据成员或引用数据成员,无...

铂金小猴
2012/05/06
0
0
C++雾中风景10:聊聊左值,纯右值与将亡值

C++11的版本在类型系统上下了很大的功夫,添加了诸如auto,decltype,move等新的关键词来简化代码的编写与降低阅读代码的难度。为了更好的理解这些新的语义,笔者确定通过几篇文章来简单窥探...

HappenLee
2018/07/19
0
0

没有更多内容

加载失败,请刷新页面

加载更多

大数据教程(11.9)hive操作基础知识

上一篇博客分享了hive的简介和初体验,本节博主将继续分享一些hive的操作的基础知识。 DDL操作 (1)创建表 #建表语法CREATE [EXTERNAL] TABLE [IF NOT EXISTS] table_name [(col_name ...

em_aaron
今天
0
0
OSChina 周四乱弹 —— 我家猫真会后空翻

Osc乱弹歌单(2019)请戳(这里) 【今日歌曲】 @我没有抓狂 :#今天听这个# 我艇牛逼,百听不厌,太好听辣 分享 Led Zeppelin 的歌曲《Stairway To Heaven》 《Stairway To Heaven》- Led Z...

小小编辑
今天
2
0
node调用dll

先安装python2.7 安装node-gyp cnpm install node-gyp -g 新建一个Electron-vue项目(案例用Electron-vue) vue init simulatedgreg/electron-vue my-project 安装electron-rebuild cnpm ins......

Chason-洪
今天
3
0
scala学习(一)

学习Spark之前需要学习Scala。 参考学习的书籍:快学Scala

柠檬果过
今天
3
0
通俗易懂解释网络工程中的技术,如STP,HSRP等

导读 在面试时,比如被问到HSRP的主备切换时间时多久,STP几个状态的停留时间,自己知道有这些东西,但在工作中不会经常用到,就老是记不住,觉得可能还是自己基础不够牢固,知识掌握不够全面...

问题终结者
昨天
4
0

没有更多内容

加载失败,请刷新页面

加载更多

返回顶部
顶部