繁体   English   中英

编译器警告“有效C ++”方法,以避免const和非const成员函数重复

[英]Compiler warning on “Effective C++”s method to avoid duplication in const and non-const member functions

该问题已更新。 请检查代码。

以下代码是使用VC ++ 2012年11月CTP编译的。 斯科特·迈耶斯(Scott Meyers)的著作《 有效的C ++ 》建议,我们应使用避免在const和非const成员函数中重复的方法。 但是,以下代码会引发警告(级别1)。 由于WDK构建工具将警告视为错误,因此以下代码无法成功编译。

还有其他更好的方法吗?

struct A
{
    int n;

    A(int n)
        : n(n)
    {}

    int Get() const
    {
        return n;
    }

    int Get()
    {
        return static_cast<const decltype(*this)&>(*this).Get();
    }
};

int main()
{
    const A a(8);

    //
    // warning C4717: 'A::Get' : recursive on all control paths,
    // function will cause runtime stack overflow
    //
    a.Get(); 
}

您已经转换了两个Get方法的主体,因此编译器是正确的。 const Get方法正在调用自身。 您现在不高兴您的构建工具将警告视为错误吗? :)

交换它们:

int& Get()
{
    return const_cast<int&>(static_cast<const A&>(*this).Get());
}

const int& Get() const
{
    return n;
}

我相信你会逆转。 这是非const版本,将constness抛弃在const版本上。

请参阅: 优雅的解决方案,以复制,const和非const,吸气剂?

回答更新的问题。 (您应该使这个问题成为新问题)

static_cast<const decltype(*this)&>(*this)*this是类型A的左值,因此,由decltype(*this)表示的类型为A& (请参见7.1.6.2 [dcl.type.simple] / 4)。

结果,您的非常量Get()函数等效于:

int Get()
{
    typedef A & Aref;
    // IMHO a const_cast would be the better choice here
    return static_cast<const Aref&>(*this).Get();
}

引用类型上的cv限定词将被忽略。 通过引用折叠,您的类型转换最终等于static_cast<A&>(*this) ,因此您无需添加所需的const。

因此,在此处无法使用decl_type 如果您非常想使用它,则需要:

int Get()
{
    // Made my suggested change of cast here
    return const_cast<const std::remove_reference<decltype(*this)>::type&>(*this).Get();
}

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM