【发布时间】:2014-05-04 13:41:46
【问题描述】:
我尝试在 XCode 5.1 上使用 c++11 构建以下代码:
template<class T>
float calc2(std::function<float(T)> f) { return -1.0f * f(3.3f) + 666.0f; }
int main(int argc, const char* argv[])
{
calc2([](float arg) -> float{ return arg * 0.5f; }); //(1) - Will not compile - no matching function...
calc2<float>([](float arg) -> float{ return arg * 0.5f; }); // (2) - Compiles well
return 0;
}
有人可以解释为什么 (1) 不能编译吗?编译器不应该从 lambda 定义中推导出 T 吗?
谢谢!
【问题讨论】:
-
std::function可能用词不当,它是一个函数包装器。 Lambda表达式具有与std::function无关的唯一类型,因此模板类型推导无法成功。 -
你只能从你直接传入的东西中推断出来,而不是从可以转换为其他东西的东西中推断出来。例如。试试
calc2(std::function<float(float)>([](float arg){return arg/2;}))。 -
那么,如果我想强制执行 calc2 接收的函数/lambda 的输入/输出参数,正确的方法是什么?
-
这就像一个概念。不幸的是,这在 C++11 中不容易做到。例如,您可以尝试
template<class F, class = typename std::enable_if< std::is_convertible<typename std::result_of<F(float)>::type, float>{} >::type> float calc2(F f);