我有一个名为x
的函数,它返回一个已知值并具有已知参数:
int x(int y);
我还有其他地方,我想创建一个容器来包含此函数的n
次调用。然后我想多次执行它。
问题是,我不想依赖它是int
返回类型。我需要在编译时推断出返回类型。类似的东西:
std::vector<result_of<x(int)>::type> results;
但我不想指定参数值,因为它们是静态的。
答案 0 :(得分:6)
您可以创建自己的特征,例如:
template <typename F> struct my_result_of;
template <typename F> struct my_result_of<F*> : my_result_of<F> {};
template <typename Ret, typename ... Ts>
struct my_result_of<Ret(Ts...)>
{
using type = Ret;
};
template <typename F> using my_result_of_t = typename my_result_of<F>::type;
并使用它(假设没有x
的重载):
std::vector<my_result_of_t<decltype(x)>::type> results;
答案 1 :(得分:5)
你很亲密。假设T
是调用函数的模板参数:
std::vector<decltype(x(std::declval<T>()))> results;
答案 2 :(得分:2)
您可以滥用std::function::result_type
:
int x(int y);
static_assert(std::is_same_v<int,std::function<decltype(x)>::result_type>);
当然,这仅在x
真正起作用时才有效。如果x
是任意函数对象,则其结果类型可能取决于其参数类型,在这种情况下,如果不指定参数,则无法知道其结果类型。
答案 3 :(得分:2)
我认为您可以使用最新的标准版本,因为您没有指定它 这是一个最小的工作示例:
#include<vector>
#include<functional>
#include<utility>
template<std::size_t... I, typename F, typename... A>
auto gen(std::index_sequence<I...>, F &&f, A... args) {
return std::vector<decltype(std::forward<F>(f)(args...))>{
(I, std::forward<F>(f)(args...))...
};
}
template<std::size_t N, typename F, typename... A>
auto gen(F &&f, A... args) {
return gen(std::make_index_sequence<N>{}, std::forward<F>(f), args...);
}
int f(int, char) { return 0; }
int main() {
auto vec = gen<10>(&f, 0, 'c');
}
您的功能的返回类型很容易推断:
decltype(std::forward<F>(f)(args...))
我想创建一个容器来包含n个这个函数的调用。然后我想多次执行它。
为此,我使用std::index_sequence
创建了一个大小合适的参数包
然后矢量本身初始化如下:
(I, std::forward<F>(f)(args...))...
基本思想是利用逗号运算符解包上面提到的参数包并执行N
次函数。 f
的调用返回的值用于填充向量。
请注意,args
并未完美转发至f
如果在第一次执行期间消耗了可移动对象,则可能会导致问题。