Generic conversion operator templates and move semantics: any universal solution?

六月ゝ 毕业季﹏ 提交于 2019-12-03 10:39:25

The C++ standard unfortunately does not have any special rule to resolve this particular ambiguity. The problem come from the fact that you are trying to overload on 2 different things: the type that the compiler is trying to convert to; and the kind of reference from which you are trying to convert from.

By introducing proxy classes, you can split the resolution in 2 steps. Step 1: decide if it's an r-value reference, an l-value reference, or a const l-value reference. Step 2: convert to any type, keeping the decision made in step 1 about the kind of reference. That way, you can use your solution with a cast() function but save you from having to specify the type:

struct A
{
    class A_r_ref
    {
        A* a_;
    public:
        A_r_ref(A* a) : a_(a) {}
        template <typename T> operator T&&() const&&;
    };

    struct A_ref
    {
        A* a_;
    public:
        A_ref(A* a) : a_(a) {}
        template <typename T> operator T&() const&&;
    };

    struct A_const_ref
    {
        const A* a_;
    public:
        A_const_ref(const A* a) : a_(a) {}
        template <typename T> operator const T&() const&&;
    };

    A_r_ref cast() && { return A_r_ref(this); }
    A_ref cast() & { return A_ref(this); }
    A_const_ref cast() const& { return A_const_ref(this); }
};
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!