【问题标题】:C++ template argument deduction is failing with error "candidate template ignored" when arguments include std::function... why? [duplicate]当参数包含 std::function 时,C++ 模板参数推导失败并出现错误“候选模板被忽略”......为什么? [复制]
【发布时间】:2016-07-29 22:13:05
【问题描述】:

我有以下功能:

template <class InType, class OutType>
OutType foo(const InType &a, std::function<OutType (const InType &)> func)
{
    return func(a);
}

template <class T>
T bar(T a, T b)
{
    return a + b;
}

我可以这样称呼他们:

double x = foo<int, double>(1, [] (const int &v) { return float(v) * 1.5f; });
double y = bar<int>(1.0, 2.0);

...并使用带 bar 的模板参数推导

double z = bar(1.0, 2.0);

...但是如果我尝试对 foo 使用模板参数推导:

double w = foo(1, [] (const int &v) { return float(v) * 1.5f; });

失败并出现此错误:

no matching function for call to 'foo'
    double w = foo(1, [] (const int &v) { return float(v) * 1.5f; });
               ^~~
note: candidate template ignored: could not match 'function<type-parameter-0-1 (const type-parameter-0-0 &)>' against '(lambda at ../path/to/file.cpp:x:y)'
OutType foo(const InType &a, std::function<OutType (const InType &)> func)
        ^

这是为什么呢?从我的角度来看,很明显应该将参数类型推断为什么。

【问题讨论】:

    标签: c++ templates template-argument-deduction


    【解决方案1】:

    类型推导不考虑隐式转换,这种转换稍后会在重载解析期间发生。如果您要直接传递 std::function ,它将正确推断。如果没有 std::function 的类型,它就不能从你的 lambda 隐式构造一个 std::function 来知道它是否可能。我知道我们似乎有足够的信息让编译器正确推断出所涉及的类型,但这是一个约束。

    【讨论】:

    • 类型推导只考虑一些隐式转换。不涉及转换构造函数。
    • 这种情况太糟糕了。否则,可以在没有 C++ 典型的冗长和模板恶作剧的情况下表达一些强大的逻辑。
    猜你喜欢
    • 1970-01-01
    • 2012-09-15
    • 2012-02-07
    • 1970-01-01
    • 2011-07-28
    • 1970-01-01
    • 2020-01-27
    • 2023-03-06
    相关资源
    最近更新 更多