【问题标题】:How to make a function wrapper that can wrap any function?如何制作可以包装任何函数的函数包装器?
【发布时间】:2020-08-31 12:20:51
【问题描述】:
#include <iostream>
#include <string>

template<typename Func>
class FuncWrapper {
    Func func;
    std::string name;

public:

    FuncWrapper(Func func, std::string name) : func(func), name(std::move(name)) {}

    template<typename ...Args>
    auto operator()(Args ...args) {
        std::cout << "Entering " + name + '\n';
        auto ret = func(args...);
        std::cout << "Exiting " + name + "\n\n";
        return ret;
    }
};

template<typename Func>
auto makeFuncWrapper(Func func, std::string name) {
    return FuncWrapper<Func>(func, name);
}

int main() {

    auto helloWorld = []() { std::cout << "Hello World\n"; };
    auto addTwoNums = [](int a, int b) { std::cout << "Adding numbers...\n"; return a + b; };

    // makeFuncWrapper(helloWorld, "helloWorld")(); // error: 'void ret' has incomplete type.
    std::cout << makeFuncWrapper(addTwoNums, "addTwoNums")(4, 5) << '\n';

}

此类FuncWrapper 工作正常,并为传递的函数添加了额外的功能,直到传递的函数是返回void 的函数。我收到ret 的类型不完整的错误。即使使用返回类型为void 的函数,还有其他方法可以使它工作吗?我知道我不能有void 变量,但在这里,ret 的唯一目的是在函数完成后返回,并且不会以错误的方式使用它。是否有解决方案或一些解决方法使其工作?有没有更好的方法来实现包装任何函数的函数包装器?

【问题讨论】:

  • 取决于 ypu 使用什么标准,您要么创建一个 SFINAE 方案,要么使用 if constrexpr 与“包装器”周围的“包装器”,这将为无效和非无效结果提供服务。另外,如果您想接受其他 callable ,例如lsmbdas,您也必须单独为它们服务。你的包装看起来像std::invoke,它的样板代码很大。
  • 注意:lambda表达式的结果不是一个函数,它是一个定义了operator()的类类型的实例。

标签: c++ templates wrapper void


【解决方案1】:

您可能会使用 Raii:

template<typename ...Args>
auto operator()(Args ...args) {
    struct EndScope {
        std::string& name;
        ~EndScope() { std::cout << "Exiting " + name + "\n\n"; }
    } endScope(name);

    std::cout << "Entering " + name + '\n';
    return func(args...);
}

您可以通过std::uncaught_exceptions 进一步处理异常

raii-way-to-get-errors-that-are-caught-during-destruction

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2021-02-27
    • 2019-08-03
    • 1970-01-01
    • 1970-01-01
    • 2011-02-09
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多