gpt4 book ai didi

c++ - 管理 C++ 委托(delegate)生命周期

转载 作者:搜寻专家 更新时间:2023-10-31 01:04:25 26 4
gpt4 key购买 nike

我看到了以下博客文章,其中解释了如何使用可变参数模板构建 C++ 委托(delegate):http://blog.coldflake.com/posts/2014-01-12-C++-delegates-on-steroids.html

我在此处复制了帖子中的 Delegate 类:

template<typename return_type, typename... params>
class Delegate
{
typedef return_type (*Type)(void* callee, params...);
public:
Delegate(void* callee, Type function)
: fpCallee(callee)
, fpCallbackFunction(function) {}

template <class T, return_type (T::*TMethod)(params...)>
static Delegate from_function(T* callee)
{
Delegate d(callee, &methodCaller<T, TMethod>);
return d;
}

return_type operator()(params... xs) const
{
return (*fpCallbackFunction)(fpCallee, xs...);
}

private:

void* fpCallee;
Type fpCallbackFunction;

template <class T, return_type (T::*TMethod)(params...)>
static return_type methodCaller(void* callee, params... xs)
{
T* p = static_cast<T*>(callee);
return (p->*TMethod)(xs...);
}
};

此处给出了如何使用该类的示例:

class A
{
public:
int foo(int x)
{
return x*x;
}
int bar(int x, int y, char a)
{
return x*y;
}
};
int main()
{
A a;
auto d = Delegate<int, int>::from_function<A, &A::foo>(&a);
auto d2 = Delegate<int, int, int, char>::from_function<A, &A::bar>(&a);
printf("delegate with return value: d(42)=%d\n", d(42));
printf("for d2: d2(42, 2, 'a')=%d\n", d2(42, 2, 'a'));
return 0;
}

这项技术非常酷,除了我还想让 Delegate 类管理被调用者的生命周期(换句话说,我想在堆上实例化 A,当 Delegate 实例被删除或超出范围时,它还应该能够删除被调用者(在这种情况下是 A 实例))。有没有简单的方法可以做到这一点?我错过了什么吗?一种解决方案是同时传递一个删除器对象,该对象会将 void* fpCallee 转换为正确的类型,然后对其调用 delete。有更好的解决方案吗?

最佳答案

你可以使用 shared_ptr<void>存储被调用者而不是 void* (请参阅 this question 了解为什么这不会导致删除问题;感谢 Kindread)。这将要求您将每个被调用者保留在 shared_ptr 中。 ,但如果您不介意,它会解决您的问题。

虽然这不是问题的答案,但您可以使用 lambda 而不是 Delegate 来完成几乎相同的事情。 :

auto a = std::make_shared<A>();
auto d = [a](int x) { a->foo(x); };

关于c++ - 管理 C++ 委托(delegate)生命周期,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/23994440/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com