c++ - 返回右值时 VS2013 警告 C4172

标签 c++ c++11 visual-studio-2013 type-erasure rvalue

Rvalues 是新的,所以我对此有些怀疑......

VS2013给出

warning C4172: returning address of local variable or temporary

对于这一行

return (std::wstring&&)         (*(std::wstring*)v);

此代码(下方)是否不可移植和/或在任何地方都有未定义的行为?如果有-在哪里以及为什么?难道我做错了什么? 或者这只是 VS2013 编译器的误报警告,在这种特殊情况下我应该只使用编译指示忽略它?

temp_value_t 旨在用作级联调用的容器:

[输入值] -> 调用 virtual_func1(temp_value_t) -> 调用 virtual_func2(temp_value_t) -> ... -> 调用 virtual_funcLAST(temp_value_t)

funcLAST 实现知道 temp_value_t 是右值还是左值,所以 funcLAST 知道应该使用哪个函数。

#include "stdafx.h"

class temp_value_t
    {
    private:
        intptr_t v;
    public:
        temp_value_t(const std::wstring& s)
            {
            v = (intptr_t)&s;
            };

        temp_value_t(std::wstring&& s)
            {
            v = (intptr_t)&s;
            };

        std::wstring&& get_as_temp()
            {
            return (std::wstring&&)         (*(std::wstring*)v);
            };

        const std::wstring& get_as_const()
            {
            return (const std::wstring&)    (*(std::wstring*)v);
            };
    };

void test(temp_value_t v, bool is_param_const)
    {
    std::wstring s;

    if(is_param_const)
        s = v.get_as_const();
    else
        s = v.get_as_temp();

    std::wcout <<  L"Inner = '" << s << L"'\n";
    }; 

int _tmain(int argc, _TCHAR* argv[])
    {
    {
    std::wcout <<  L"Test with temp:\n";
    std::wstring s(L"abc");
    test(s, false);
    std::wcout <<  L"Outer = '" << s << L"'\n";
    }

    std::wcout <<  L"\n\n";

    {
    std::wcout <<  L"Test with const:\n";
    std::wstring s(L"abc");
    test(s, true);
    std::wcout <<  L"Outer = '" << s << L"'\n";
    }

    return 0;
    }

/*
VS2013 results:
    Test with temp:
    Inner = 'abc'
    Outer = ''


    Test with const:
    Inner = 'abc'
    Outer = 'abc'

So all works fine... 
*/

最佳答案

为什么不存储给定字符串的引用?

class temp_value_t
{
    private:
        const std::wstring & v;
    public:
        temp_value_t(const std::wstring & s)
            : v(s)
        {
        }

        // You can't store reference if you are expecting an rvalue.
        // Because, that rvalue is going to or may expire soon,
        // and when that happens, the stored reference will be invalid.
        //temp_value_t(std::wstring && s)
        //  : v(std::move(s))
        //{
        //}

        // This will already return an rvalue.
        // It is meaningless to cast it to (std::wstring&&).
        std::wstring get_as_temp()
        {
            return v;
        }

        const std::wstring & get_as_const()
        {
            return v;
        }
};

如果您的目标是存储一个作为右值引用传递的字符串对象,请定义一个移动构造函数,并将右值字符串本地存储在对象中。

关于c++ - 返回右值时 VS2013 警告 C4172,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/33516579/

相关文章:

c++ - C++ 或任何其他语言的可选结构类型可能性?

c++ - 开关盒中的多个条件?

c++ - 用名称标记 std::function?

c++ - OpenCV:minMaxIdx 之后的堆栈损坏

c# - 从类继承时编译错误

c++ - 错误 : expected unqualified-id on extern "C"

C++ String.h Char Tables 没有 strstr 的截断词

c++ - 具有两个原子的自旋锁的最小限制内存排序

c++ - 将字符串转换为数字以便更快地比较它们

c++ - Visual Studio 2013 Professional 中的 DLL 分析找不到 VSPerfControl.Interop