从参数的返回类型推断类型

Inferring type from argument's return type

本文关键字:类型 返回类型 参数      更新时间:2023-10-16

我知道模板无法从赋值推断出类型,即

template <typename T>
T aFunction (int a) { /*...*/ }; // This obviously won't work

原因很明显。但这将起作用:

template <typename T>
T aFunction (T a, T b) { return a + b; }; // a-ok

"因为T将从论点中推断出来。我想从中推断一下:

template <typename T>
T aFunction (std::function<T(int)> a) { return a(3);};
^
|
I specified it! ----------

因此,在使用时,函数应该做什么没有歧义:

std::function<double(int)> blah = [](int x){ return x / 2.0f; };
aFunction(blah);

唉,编译器不会和我合作:

没有匹配的成员函数来调用"aFunction">

忽略候选模板:不匹配 'function' against '(lambda at 文件.hpp:274:16)'

有没有办法做到这一点?,除了模板专业化(这是一个非常通用的类)或虚拟论点(我还没那么绝望)。


目录:

完全披露:以上只是对问题的简化,正是我需要的是:

template <typename T>
class MyStuff {
template <typename ReturnType>
MyStuff<ReturnType> aFunction(std::function<ReturnType(T)> a){ 
/*for each stuff in MyStuff do a(stuff)*/ 
}
}

其中MyStuff包含类型T的属性和一堆inline函数,例如aFunction

如评论中所述,这有效:

#include <functional>
template <typename T>
struct MyStuff {
template <typename ReturnType>
MyStuff<ReturnType> aFunction(std::function<ReturnType(T)> a){ 
return {};
}
};
int main() {
MyStuff<int> stuff;
std::function<double(int)> fn = [](int) { return 0.; };
stuff.aFunction(fn);
}

相反,这不起作用:

int main() {
MyStuff<int> stuff;
stuff.aFunction([](int) { return 0.; });
}

错误是问题中发布的错误:

注意:候选模板被忽略:无法将"函数"与"(主.cpp:15:21的 lambda)"匹配

原因是类型推断仅适用于确切类型。不允许转换。在您的情况下,编译器应首先推断 lambda 的返回类型,然后以某种方式将其转换为std::function,最后从使用 lambda 构造的返回类型中推断出函数的返回类型。
这不是类型推断的工作方式。

您可以使用如下方法解决它:

template <typename T>
struct MyStuff {
template <typename F>
auto aFunction(F &&f) -> MyStuff<decltype(std::forward<F>(f)(std::declval<T>()))> { 
return {};
}
};

在科利鲁看到它。