c++11中关于什么是lvalue, 什么是rvalue, 什么是xvalue, 什么是prvalue, 什么是…

一直搞得我晕头转向的, 今天下定决心一定要把它搞定, 写了一个程序来判断lvalue, rvalue, prvalue等

 namespace test{

 template <typename T>
struct is_lvalue_reference {
const static bool value = false;
}; template <typename T>
struct is_lvalue_reference<T&> {
const static bool value = true;
}; template <typename T>
struct is_rvalue_reference {
const static bool value = false;
}; template <typename T>
struct is_rvalue_reference<T&&> {
const static bool value = true;
}; template <typename T>
struct is_xvalue {
const static bool value = (!is_lvalue_reference<T>::value) && is_rvalue_reference<T>::value;
}; template <typename T>
struct is_prvalue {
const static bool value = !(is_lvalue_reference<T>::value || is_rvalue_reference<T>::value);
}; template <typename T>
struct is_lvalue {
const static bool value = !(is_xvalue<T>::value || is_prvalue<T>::value);
}; template <typename T>
struct is_rvalue {
const static bool value = (is_xvalue<T>::value || is_prvalue<T>::value);
}; template <typename T>
struct is_glvalue{
const static bool value = (is_xvalue<T>::value || is_lvalue<T>::value);
}; }

测试验证:

 struct Foo {};
Foo funRetFoo();
Foo& funRetFooLRef();
Foo&& funRetFooRRef(); TEST(TypeTraits, isRvalue){ //base type
EXPECT_FALSE(::test::is_lvalue_reference<int>::value);
EXPECT_FALSE(::test::is_rvalue_reference<int>::value);
EXPECT_FALSE(::test::is_lvalue<int>::value);
EXPECT_FALSE(::test::is_xvalue<int>::value);
EXPECT_TRUE(::test::is_prvalue<int>::value);
EXPECT_FALSE(::test::is_glvalue<int>::value);
EXPECT_TRUE(::test::is_rvalue<int>::value); // return obj
EXPECT_FALSE(::test::is_lvalue_reference<decltype(funRetFoo())>::value);
EXPECT_FALSE(::test::is_rvalue_reference<decltype(funRetFoo())>::value);
EXPECT_FALSE(::test::is_lvalue<decltype(funRetFoo())>::value);
EXPECT_FALSE(::test::is_xvalue<decltype(funRetFoo())>::value);
EXPECT_TRUE(::test::is_prvalue<decltype(funRetFoo())>::value);
EXPECT_FALSE(::test::is_glvalue<decltype(funRetFoo())>::value);
EXPECT_TRUE(::test::is_rvalue<decltype(funRetFoo())>::value); // return ref obj
EXPECT_TRUE(::test::is_lvalue_reference<decltype(funRetFooLRef())>::value);
EXPECT_FALSE(::test::is_rvalue_reference<decltype(funRetFooLRef())>::value);
EXPECT_TRUE(::test::is_lvalue<decltype(funRetFooLRef())>::value);
EXPECT_FALSE(::test::is_xvalue<decltype(funRetFooLRef())>::value);
EXPECT_FALSE(::test::is_prvalue<decltype(funRetFooLRef())>::value);
EXPECT_TRUE(::test::is_glvalue<decltype(funRetFooLRef())>::value);
EXPECT_FALSE(::test::is_rvalue<decltype(funRetFooLRef())>::value); // return rref obj
EXPECT_FALSE(::test::is_lvalue_reference<decltype(funRetFooRRef())>::value);
EXPECT_TRUE(::test::is_rvalue_reference<decltype(funRetFooRRef())>::value);
EXPECT_FALSE(::test::is_lvalue<decltype(funRetFooRRef())>::value);
EXPECT_TRUE(::test::is_xvalue<decltype(funRetFooRRef())>::value);
EXPECT_FALSE(::test::is_prvalue<decltype(funRetFooRRef())>::value);
EXPECT_TRUE(::test::is_glvalue<decltype(funRetFooRRef())>::value);
EXPECT_TRUE(::test::is_rvalue<decltype(funRetFooRRef())>::value); int lvalue;
// 模拟=号左边
EXPECT_TRUE(::test::is_lvalue_reference<decltype(*&lvalue)>::value);
EXPECT_FALSE(::test::is_rvalue_reference<decltype(*&lvalue)>::value);
EXPECT_TRUE(::test::is_lvalue<decltype(*&lvalue)>::value);
EXPECT_FALSE(::test::is_xvalue<decltype(*&lvalue)>::value);
EXPECT_FALSE(::test::is_prvalue<decltype(*&lvalue)>::value);
EXPECT_TRUE(::test::is_glvalue<decltype(*&lvalue)>::value);
EXPECT_FALSE(::test::is_rvalue<decltype(*&lvalue)>::value); //operator++()
EXPECT_FALSE(::test::is_lvalue_reference<decltype(lvalue++)>::value);
EXPECT_FALSE(::test::is_rvalue_reference<decltype(lvalue++)>::value);
EXPECT_FALSE(::test::is_lvalue<decltype(lvalue++)>::value);
EXPECT_FALSE(::test::is_xvalue<decltype(lvalue++)>::value);
EXPECT_TRUE(::test::is_prvalue<decltype(lvalue++)>::value);
EXPECT_FALSE(::test::is_glvalue<decltype(lvalue++)>::value);
EXPECT_TRUE(::test::is_rvalue<decltype(lvalue++)>::value); //operator++(int)
EXPECT_TRUE(::test::is_lvalue_reference<decltype(++lvalue)>::value);
EXPECT_FALSE(::test::is_rvalue_reference<decltype(++lvalue)>::value);
EXPECT_TRUE(::test::is_lvalue<decltype(++lvalue)>::value);
EXPECT_FALSE(::test::is_xvalue<decltype(++lvalue)>::value);
EXPECT_FALSE(::test::is_prvalue<decltype(++lvalue)>::value);
EXPECT_TRUE(::test::is_glvalue<decltype(++lvalue)>::value);
EXPECT_FALSE(::test::is_rvalue<decltype(++lvalue)>::value); }

Lvalue, Rvalue, Xvalue, Prvalue, Glvalue的更多相关文章

  1. C++ lvalue,prvalue,xvalue,glvalue和rvalue详解(from cppreference)

    General 每一个C++表达式(一个操作符和它的操作数,一个字面值,一个变量名等等)都代表着两个独立属性:类型+属性分类.在现代C++中 glvalue(泛左值) = lvalue (传统意义上的 ...

  2. lvalue & rvalue

    https://www.youtube.com/watch?v=UTUdhjzws5g 作者:知乎用户链接:https://www.zhihu.com/question/50652989/answer ...

  3. C++98/11/17表达式类别

    目标 以下代码能否编译通过,能否按照期望运行?(点击展开) #include <utility> #include <type_traits> namespace cpp98 ...

  4. 理解lvalue和rvalue

    今天看C++模板的资料,里面说到lvalue,rvalue的问题,这个问题以前也看到过,也查过相关资料,但是没有考虑得很深,只知道rvalue不能取地址,不能赋值等等一些规则.今天则突然有了更深层次的 ...

  5. Value Categories

    Value categories Three primary categories primary categories mixed special Each C++ expression (an o ...

  6. C++11的value category(值类别)以及move semantics(移动语义)

    转载请保留以下声明 作者:赵宗晟 出处:http://www.cnblogs.com/zhao-zongsheng/p/value_categories_and_move_semantics.html ...

  7. C++ 新特性 笔记

    摘录 constexptr C++14尝鲜:constexpr函数(编译期函数) 总结来说,就是在c++11之前,要实现编译期数值计算需要繁琐的模板元编程.在c++11 中,可以是函数,在一句rutu ...

  8. C++11引用临时变量的终极解析

    工作中遇到一个引用临时变量的问题,经过两天的学习,私以为:不仅弄明白了这个问题,还有些自己的独到见解. 这里使用一个简单的例子来把自己的学习过程和理解献给大家,如果有什么问题请不吝指正.   **** ...

  9. 对C++11中的`移动语义`与`右值引用`的介绍与讨论

    本文主要介绍了C++11中的移动语义与右值引用, 并且对其中的一些坑做了深入的讨论. 在正式介绍这部分内容之前, 我们先介绍一下rule of three/five原则, 与copy-and-swap ...

随机推荐

  1. 设计模式 命令-Command

    命令-Command 当要向不同类的对象发出相同的请求时,可以将接收者和他的动作封装进一个命令对象.这样调用者只和命令产生依赖.而不会和众多的接收者发生依赖. Head First例子 要设计一款遥控 ...

  2. Hadoop2.2 federnation联盟的搭建

    联盟实际上是一个单独的集群,集群里面包含很多的NameService共享同样的DataNode,同一份数据只上传一份,block块相同,一个集群中删除,另一个集群中还是存在的.同一份数据只是在name ...

  3. iOS打开手机QQ与指定用户聊天界面

    开发中遇到一个联系客服qq的需求,找到这么一个实现方法,先记录下来.大概的原理就是,iOS启动第三方应用是采用schema模式的,这有点像url,打开不同的界面使用不同的地址.但这个url怎么得来的还 ...

  4. U盘分区信息清除

    diskpart select disk 1 clean 清除选中(优U)盘的所有信息;

  5. 思科ASA系列防火墙配置手册

    使用console连接线登录方法 1.使用cisco的console连接线,连接设备的console口和计算机com口(笔记本用USB转COM口连接线)2.使用超级终端或secureCRT软件连接设备 ...

  6. Python基础 初识Python

    机器码 机器码(machine code),学名机器语言指令,有时也被称为原生码(Native Code),是电脑的CPU可直接解读的数据. 通常意义上来理解的话,机器码就是计算机可以直接执行,并且执 ...

  7. miniui datagrid 保存到服务端,使用.NET 自带 JSON 转换时发现日期格式不兼容。

    使用 miniui datagrid 修改表格后,保存到服务端,然后使用 .NET 自带 JSON 转换,会抛出DateTime 内容“2015-12-27T11:02:28”未按 JSON 的要求以 ...

  8. 计数排序详解以及java实现

    前言 我们知道,通过比较两个数大小来进行排序的算法(比如插入排序,合并排序,以及上文提到的快速排序等)的时间复杂度至少是Θ(nlgn),这是因为比较排序对应的决策树的高度至少是Θ(nlgn),所以排序 ...

  9. Could not load file or assembly 'MagickNet.dll'

    1  确定项目中bin目录下存在该DLL文件 2   安装 VC++发布组件_缩略图用_x86(1).exe

  10. C:指针、数据类型、格式化输入输出、输入函数的坑点

    指针.数据类型.格式化输入输出.输入函数的坑点 有时候我们迷茫的时候,坚持就是最好的选择. 1.指针的分类为什么很重要? 参考 答:因为指针会根据相应的类型取对应长度的数据,类型决定所取数据的长度.如 ...