如何声明没有std::function的函数返回函数
C++ How to declare function-returning function without std::function?
尝试一些构图的想法,我有
#include <iostream>
#include <functional>
using namespace std;
struct A { };
struct B { };
struct C { };
B b4a (A a) { B b; return b; }
C c4b (B b) { C c; return c; }
template <typename R, typename S, typename T>
function<R(T)> composition
( R(r4s)(S)
, S(s4t)(T) )
{ return [=] (T t) { return r4s (s4t (t)); }; }
int main()
{
cout << "b4a : " << type_name<decltype(b4a)>() << endl;
cout << "c4b : " << type_name<decltype(c4b)>() << endl;
auto c4a = composition<C, B, A> (c4b, b4a);
cout << "c4a : " << type_name<decltype(c4a)>() << endl;
auto lb4a = [=] (A a) { B b; return b; };
auto lc4b = [=] (B b) { C c; return c; };
auto lc4a = composition<C, B, A>(lc4b, lb4a);
cout << "lc4a : " << type_name<decltype(lc4a)>() << endl;
}
(type_name
的定义有点偏离主题,但是您可以在这里看到上面的完整工作示例)。
可以看到,composition
操作符既适用于函数指针(如b4a
),也适用于lambda指针(如lb4a
)。我想摆脱composition
的function<R(T)>
返回类型,只是直接声明它的类型,但我不知道如何以任何其他方式表示它的返回类型。尝试
R(composition)(T)
或
R(*composition)(T)
或
R(&composition)(T)
产生'composition' declared as function returning a function
,让我怀疑这是不可能的。线索吗?
lambda具有唯一但未指定的类型。一种可能的解决方法是不使用lambdas,而是创建自己的等效类:
template <typename R, typename S, typename T>
struct Composition {
R (*r4s)(S);
S (*s4t)(T);
R operator()(T t) const { return r4s(s4t(t)); }
};
template <typename R, typename S, typename T>
Composition<R,S,T> composition(R (*r4s)(S),S(*s4t)(T))
{
return {r4s,s4t};
}
不可能在运行时创建新函数。创建lambda只是创建lambda闭包类型的一个实例(它是一个类),但是函数本身是在编译时作为类的operator()
创建的。
lambda表达式捕获的函数指针r4s
和s4t
成为闭包对象的成员。如果您真的可以创建r4s
和s4t
的组合作为一个新函数,那么可以说,它们将"嵌入到代码中"。这类事情在c++中是不可能完成的。
您应该像这里一样使用std::function
@Vaughn Cato的回答(现场演示)的一个通用的,可变的变体:
template <typename...>
class Composition {
// This "base case" is only used for zero-function compositions.
public:
void operator () () {}
};
template <typename F, typename... Remainder>
class Composition<F, Remainder...> : private Composition<Remainder...> {
// This specialization matches all non-zero function compositions.
using base_t = Composition<Remainder...>;
F f_;
// Use tag dispatching to determine if F is the last function in
// the composition, and should be called with the args, or
// if there are further functions and f should be called with
// the result of passing the args on to the other functions.
using is_last = std::integral_constant<bool, sizeof...(Remainder) == 0>;
template <typename... Args>
auto dispatch(std::true_type, Args&&... args) ->
decltype(f_(std::forward<Args>(args)...)) {
return f_(std::forward<Args>(args)...);
}
template <typename... Args>
auto dispatch(std::false_type, Args&&... args) ->
decltype(f_(std::declval<base_t&>()(std::forward<Args>(args)...))) {
return f_(static_cast<base_t&>(*this)(std::forward<Args>(args)...));
}
public:
template <typename T, typename... Args>
Composition(T&& t, Args&&... args) :
base_t(std::forward<Args>(args)...),
f_(std::forward<T>(t)) {}
template <typename... Args>
auto operator () (Args&&... args) ->
decltype(std::declval<Composition&>().dispatch(is_last{}, std::forward<Args>(args)...)) {
return dispatch(is_last{}, std::forward<Args>(args)...);
}
};
template <typename... Functions>
inline Composition<typename std::decay<Functions>::type...>
composition(Functions&&... f)
{
return {std::forward<Functions>(f)...};
}
相关文章:
- 无法引用该函数" 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()