C++概念求助,如何理解“可修改的右值”

boot_black 2019-08-16 04:24:19


额,以我的理解,既然是右值,就类似于字面值常量,应该是不可修改的才对,如何理解“可修改的右值”?
恳请各位指教,感谢!
...全文
1819 27 打赏 收藏 转发到动态 举报
写回复
用AI写文章
27 条回复
切换为时间正序
请发表友善的回复…
发表回复
真相重于对错 2021-07-17
  • 打赏
  • 举报
回复

int&& a=100;//右值引用(c++11起)绑定一个纯右值。
a=10;//ok

真相重于对错 2021-07-17
  • 打赏
  • 举报
回复

右值
右值表达式包括纯右值、亡值。

性质:

右值不能由内建的取址运算符取地址:&int()、&i++[3]、&42 及 &std::move(x) 是非法的。
右值不能用作内建赋值运算符及内建复合赋值运算符的左操作数。
右值可以用于初始化 const 左值引用,这种情况下该右值所标识的对象的生存期被延长到该引用的作用域结尾。
右值可以用于初始化右值引用,这种情况下该右值所标识的对象的生存期被延长到该引用的作用域结尾。
当被用作函数实参且该函数有两种重载可用,其中之一接受右值引用的形参而另一个接受 const 的左值引用的形参时,右值将被绑定到右值引用的重载之上(从而,当复制与移动构造函数均可用时,以右值实参将调用其移动构造函数,复制和移动赋值运算符与此类似)。
(C++11 起)

  • 打赏
  • 举报
回复

参考16楼boot_black的回复,并且我也重翻了C++ Primer。
C++的内置数据类型作为右值,的确是不可修改的,也不可再被赋值(=);但是C++ Primer中没有说 类类型作为右值,是常量,是不可修改的,不论是C++旧标准还是C++11都是允许类类型的右值被赋值,例如std::string就是如此。类类型的右值的确是临时变量,但是类类型的临时变量是可以调用成员函数的,包括(operator=)赋值运算符重载函数,这体现在代码上就是:类类型的临时变量可以赋值。

当然,你可以尝试把(operator=)设置成删除的函数delete,这样的话,就不可以对类类型的临时变量赋值;或者你令一个函数返回const的类类型临时变量,也是无法调用(operator=)进行赋值的。

所以,右值引用可以被修改,也可以是不能被修改(const修饰)。

boot_black 2019-08-22
  • 打赏
  • 举报
回复
感谢以上各位大神的热心帮忙
chixiang1111 2019-08-21
  • 打赏
  • 举报
回复
这么理解,左值是自变量,右值是需要赋值的因变量,所以,参数可视为右值,函数返回值可视为左值,一个赋值语句左侧为左值,右侧为右值。
帐号已注消 2019-08-21
  • 打赏
  • 举报
回复
右值引用可以延长右值的生命周期,使右值不会立即销毁
xiaoxiangqing 2019-08-20
  • 打赏
  • 举报
回复
我觉得不加const的就是可以修改的
boot_black 2019-08-19
  • 打赏
  • 举报
回复 1
引用 16 楼 sdghchj 的回复:
在作者看来,const修饰的是不可修改的,没有const修饰的自然就是可修改的。
但从另一方面说,右值一般是指将亡值和字面常量,是不可修改的。右值引用可以引用左值和右值。右值引用和右值不是一个概念。而这概念也基本是在传参时参数绑定才有用,不管是引用的左值还是右值,一旦进入了函数,右值引用变量已经是具名变量,就已经是一个左值引用的左值了。
正是因为move语义是一般是用来移动右值引用内部的内存,所以肯定不能是const修饰的,也就是可修改。


==================================================

感谢指教,很专业!
sdghchj 2019-08-19
  • 打赏
  • 举报
回复
引用 18 楼 boot_black 的回复:
[quote=引用 16 楼 sdghchj 的回复:] 在作者看来,const修饰的是不可修改的,没有const修饰的自然就是可修改的。 但从另一方面说,右值一般是指将亡值和字面常量,是不可修改的。右值引用可以引用左值和右值。右值引用和右值不是一个概念。而这概念也基本是在传参时参数绑定才有用,不管是引用的左值还是右值,一旦进入了函数,右值引用变量已经是具名变量,就已经是一个左值引用的左值了。 正是因为move语义是一般是用来移动右值引用内部的内存,所以肯定不能是const修饰的,也就是可修改。
================================================== 感谢指教,很专业![/quote] 有一点说错了哈,不管是左值还是右值,进入右值引用参数的函数内部,就成了具名变量,成了右值引用的左值。
DestinedToDie 2019-08-17
  • 打赏
  • 举报
回复
引用 6 楼 weixin_44628052的回复:
没打完不慎点了提交…爪机党… 但是不可修改;表达式和函数返回值(如果返回引用好像不行吧)可以作为右值,这个可以修改
返回const值也不行
DestinedToDie 2019-08-17
  • 打赏
  • 举报
回复
没打完不慎点了提交…爪机党… 但是不可修改;表达式和函数返回值(如果返回引用好像不行吧)可以作为右值,这个可以修改
DestinedToDie 2019-08-17
  • 打赏
  • 举报
回复
左值在内存里,右值在寄存器里,字面量也是右值,但是
  • 打赏
  • 举报
回复
就是const的应用啊。 push_back(const x&);参数可以是常量,立即数,变量,变量就是可修改的右值。 push_back(x&&);只能接收变量(可修改的右值),不能接受立即数,常量。
Asome 2019-08-17
  • 打赏
  • 举报
回复
片面的总结一下,不对,请指正:1. 右值是的出现是为了解决对象复制时的性能问题;2. 右值只是语法级别概念,不需要深究,只需要知道其本质上就是将对象传递给另外的一个对象;3. 必须要注意,使用右值之后,之前的那个变量不能再使用,使用的话,可能存在潜在问题
sdghchj 2019-08-17
  • 打赏
  • 举报
回复
在作者看来,const修饰的是不可修改的,没有const修饰的自然就是可修改的。 但从另一方面说,右值一般是指将亡值和字面常量,是不可修改的。右值引用可以引用左值和右值。右值引用和右值不是一个概念。而这概念也基本是在传参时参数绑定才有用,不管是引用的左值还是右值,一旦进入了函数,右值引用变量已经是具名变量,就已经是一个左值引用的左值了。 正是因为move语义是一般是用来移动右值引用内部的内存,所以肯定不能是const修饰的,也就是可修改。
  • 举报
回复
@sdghchj 我重新翻了一下c++ primer第五版说:不能将一个右值引用直接绑定到一个左值上(P471 13.6.1右值引用);右值引用绑定到左值得通过std::move调用。也谢谢帮我重新复习了一下,右值引用和右值不是一个概念,右值引用是是必须绑定到右值的引用。
klavien 2019-08-17
  • 打赏
  • 举报
回复
首先,关于一个类的成员函数,C++11标准新增了移动构造函数,移动赋值运算符两个,你要先理解其概念。 其次,关于可修改的右值,其实就是你可以窃取(调用了移动构造函数,移动赋值运算符或显示调用std::move)它的值,而你所理解的”既然是右值,就类似于字面值常量,应该是不可修改的才对“,其实是右值无法调用的普通的拷贝构造函数和赋值运算符。 总结就是:右值和字面值常量是不一样的,你不能对一个字面值常量使用拷贝构造函数、赋值运算符、移动构造函数,移动赋值运算符任何一个,而右值不能使用拷贝构造函数、赋值运算符但可以使用移动构造函数,移动赋值运算符,所以右值是可修改的。
DestinedToDie 2019-08-17
  • 打赏
  • 举报
回复
引用 14 楼 lin5161678 的回复:
[quote=引用 13 楼 weixin_44628052 的回复:]
[quote=引用 11 楼 lin5161678 的回复:]
[quote=引用 5 楼 weixin_44628052 的回复:]
左值在内存里,右值在寄存器里,字面量也是右值,但是
C++不能这样分的
右值可以在内存里面 左值也可以在寄存器里面[/quote]
这个我是以前看别人说的,刚才又去翻了一下,你说得有道理,右值确实可以是内存里面的“将亡值”,但是左值在寄存器里有什么例子吗,我没想到[/quote]寄存器变量[/quote]多谢
lin5161678 2019-08-17
  • 打赏
  • 举报
回复
引用 13 楼 weixin_44628052 的回复:
[quote=引用 11 楼 lin5161678 的回复:] [quote=引用 5 楼 weixin_44628052 的回复:] 左值在内存里,右值在寄存器里,字面量也是右值,但是
C++不能这样分的 右值可以在内存里面 左值也可以在寄存器里面[/quote] 这个我是以前看别人说的,刚才又去翻了一下,你说得有道理,右值确实可以是内存里面的“将亡值”,但是左值在寄存器里有什么例子吗,我没想到[/quote]寄存器变量
DestinedToDie 2019-08-17
  • 打赏
  • 举报
回复
引用 11 楼 lin5161678 的回复:
[quote=引用 5 楼 weixin_44628052 的回复:]
左值在内存里,右值在寄存器里,字面量也是右值,但是
C++不能这样分的
右值可以在内存里面 左值也可以在寄存器里面[/quote]
这个我是以前看别人说的,刚才又去翻了一下,你说得有道理,右值确实可以是内存里面的“将亡值”,但是左值在寄存器里有什么例子吗,我没想到
yshuise 2019-08-17
  • 打赏
  • 举报
回复
右值不类似常量,即将消失的值
加载更多回复(6)

65,211

社区成员

发帖
与我相关
我的任务
社区描述
C++ 语言相关问题讨论,技术干货分享,前沿动态等
c++ 技术论坛(原bbs)
社区管理员
  • C++ 语言社区
  • encoderlee
  • paschen
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
  1. 请不要发布与C++技术无关的贴子
  2. 请不要发布与技术无关的招聘、广告的帖子
  3. 请尽可能的描述清楚你的问题,如果涉及到代码请尽可能的格式化一下

试试用AI创作助手写篇文章吧