【问题标题】:C++ template deduction couldn't infer template argumentC++ 模板推导无法推断模板参数
【发布时间】:2016-08-20 02:42:50
【问题描述】:

我有以下场景:

struct AP;
struct B
{
    B() : m(2) {}
    int m;
};

struct A : private B
{
    A() : B(), n(1) {}
private:
    int n;
    friend AP;
};

struct AP
{
    AP(A& a) : a_(a) {}

    template<typename T>
    struct A_B {
        using type = typename std::enable_if< std::is_base_of< typename std::remove_reference<T>::type,
                                                               A >::value,
                                                                    T >::type;
    };

    template<typename T>
    operator typename A_B<T>::type()
    {
        return static_cast<T>(a_);
    }

    template<typename T>
    typename A_B<T>::type get()
    {
        return static_cast<T>(a_);
    }

    int& n() { return a_.n; }
private:
    A& a_;
};

int main()
{
    A a;
    AP ap(a);
    ap.n() = 7;
    const B& b = ap.get<const B&>();
    //const B& b = ap; candidate template ignored: couldn't infer template argument 'T'
    //auto b = static_cast<const B&>(ap); candidate template ignored: couldn't infer template argument 'T'
    std::cout<<b.m;
}

注释行无法编译。 Clang++ 指出“候选模板被忽略:无法推断模板参数 'T'”

为什么我无法使用 cast 运算符获得对 A 基数的引用? 我认为这样代码看起来会更好。

【问题讨论】:

  • 您的注释行尝试将ap 转换为B 类型的引用,而ap 的类型为AP,与BA 无关。您希望它如何工作?
  • @wasthishelpful:我认为 OP 试图做的是将AP 实例的a_ 成员转换为B,这应该是有效的,因为A 派生自@987654332 @.

标签: c++11 casting template-meta-programming


【解决方案1】:

您发布的答案很有效,但除非您真的想要static_assert 消息,否则它是多余的。

经典模板在这种情况下工作得很好,因为A 已经可以转换为B

struct AP
{
    AP(A& a) : a_(a) {}

    template<typename T>
    operator T()
    {
        return a_;
    }

    template<typename T>
    T get()
    {
        return a_;
    }

    int& n() { return a_.n; }
private:
    A& a_;
};

Demo

【讨论】:

    【解决方案2】:

    我在这里找到了答案:http://www.mersenneforum.org/showthread.php?t=18076

    这是关键:“当你希望编译器推导出参数类型时,那些类型不能是依赖类型”

    这样就可以编译了:

    template<typename T>
    operator T()
    {
        static_assert(std::is_base_of< typename std::remove_reference<T>::type,A >::value,
                            "You may cast AP only to A's base classes.");
        return static_cast<T>(a_);
    }
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2010-12-22
      • 1970-01-01
      • 2021-07-12
      • 2013-02-18
      • 2022-12-02
      • 2023-03-31
      • 1970-01-01
      相关资源
      最近更新 更多