模板函数中的std::函数
std::function in template function
我试图编写一个模板函数,它可以接受函子作为参数,然后调用它。程序如下:
#include <iostream>
#include <functional>
using namespace std;
template<typename R, typename... Args>
R call(function<R(Args...)> fun, Args... args)
{
cout << "call@ " << __LINE__ <<endl;
return fun(args...);
}
int main()
{
cout << call(std::plus<int>(),1,2) <<endl;
return 0;
}
G++组件:
g++ -c -Wall -std=c++0x -I../include a.cpp -o a.o
a.cpp: In function ‘int main()’:
a.cpp:16:38: error: no matching function for call to ‘call(std::plus<int>, int, int)’
a.cpp:16:38: note: candidate is:
a.cpp:7:3: note: template<class R, class ... Args> R call(std::function<_Res(_ArgTypes ...)>, Args ...)
a.cpp:7:3: note: template argument deduction/substitution failed:
a.cpp:16:38: note: ‘std::plus<int>’ is not derived from ‘std::function<_Res(_ArgTypes ...)>’
make: *** [a.o] Error 1
我想std::plus<int>()
可以被推导出std::function<int(int,int)>
,但它没有。为什么?GCC是gcc version 4.7.2 20120921 (Red Hat 4.7.2-2) (GCC)
我想std::plus()可以被推导为std::function
没有。由于您传递了一个类型为std::plus<int>
的对象,因此无法推断。
在您的情况下,您不需要使用std::function
,因为通常情况下,您在存储可以使用特定签名调用的不同函数/函数对象时会使用它。
这样,您就可以让call
函数直接接受函数/函数对象,并推导出其原始类型,而无需使用std::function
。此外,您可能还希望在接受参数时使用完美转发,并在将参数作为参数传递给函数/函数对象时使用std::forward
。您还应该使用函数的返回类型作为call
的返回类型。使用C++11的尾部返回类型和decltype
。
#include <iostream>
#include <functional>
using namespace std;
template<typename R, typename... Args>
auto call(R fun, Args&&... args) -> decltype(fun(std::forward<Args>(args)...))
{
cout << "call@ " << __LINE__ <<endl;
return fun(std::forward<Args>(args)...);
}
int main()
{
cout << call(std::plus<int>(),1,2) <<endl;
return 0;
}
实时代码
正如@Jan Hudec所评论的,无论传递什么函数,其中的__LINE__
在对call
的所有调用中都将始终产生相同的结果。
它无法推导模板参数。
我建议更改函数签名,如下所示:
template<typename F, typename... Args>
auto call(F fun, Args... args )
-> decltype( fun(args...) )
在推导模板参数时不考虑大多数隐式转换。当然不是用户定义的。因此,即使plus
可以转换为function
,也没有什么区别。
相关文章:
- 无法引用该函数" std:: variant <_Types...> operator =",因为此函数已被删除
- 错误:使用已删除的函数"std::unique_ptr<...>
- 我有模板功能.通过使用函数std::for_each,用这个容器中的最大数字替换每个正数
- 如何使用函数std::min()来计算最小值
- 删除了 g++ 在 linux 中basic_stringstream函数 std
- 如何在 c++ 中使用返回类型导出函数 std::map
- 错误:使用已删除的函数"std::atomic<_Tp>::atomic() [_Tp = node]"
- 使用 SFINAE 检查函数 std::to_string 是否存在类型
- C++14 unique_ptr并使用已删除的函数'std::unique-ptr' unique_ptr错误
- 为什么函数 std::basic_streambuf::setg() 需要非常量 agruments
- C++将已删除的函数 std::unique_ptr 与基类一起使用
- 奇怪的错误:当没有真正创建指针时,使用已删除的函数'std::unique_ptr<_Tp,_Dp>::unique_ptr
- 通过模板构造函数(std ::功能和迷你案例)将构造函数触发
- 错误:使用已删除的函数"std::atomic<_Tp>::atomic()
- 错误:使用已删除的函数std::basic_ofstream(OpenCV和C++11)
- 类成员容器迭代器在成员函数std::find中不兼容,但为什么不兼容呢
- 没有构造函数 std::istream_iterator 的实例
- 错误:没有与参数列表匹配的重载函数"std::make_shared"实例
- 错误:使用已删除的函数"std::thread::thread(const std::thread&)"
- 不能在没有对象的情况下调用成员函数 std::string class::function()