难以置信的快速委托是否是std::function的合适替代品? 我最近遇到了一篇文章,叫做“不可能的快速C++代表”和它的C++ 11版本,它被称为“不可能的快速C++代表固定”,它似乎很受欢迎。它们似乎与std::function具有相同的用例,即将不同的functor类型强制为单个类型。然而,作者声称他们的表现要好得多
它们是否是std::function的合适的、性能良好的替代品?如果是这样,为什么std::function的实现方式不同?或者,不可能的快速C++代表有什么缺点? 编辑: 正如评论所要求的,“不可能的快速C++代表”的主要思想似乎是将指针存储到非类型化数据旁边,函数指针使用非指针类型的数据作为参数。“不可能的快速C++委托”扩展了以前的功能,以支持lambdas等。下面是“不可能的快速C++代表”中显示的代码摘要难以置信的快速委托是否是std::function的合适替代品? 我最近遇到了一篇文章,叫做“不可能的快速C++代表”和它的C++ 11版本,它被称为“不可能的快速C++代表固定”,它似乎很受欢迎。它们似乎与std::function具有相同的用例,即将不同的functor类型强制为单个类型。然而,作者声称他们的表现要好得多,c++,performance,delegates,compare,C++,Performance,Delegates,Compare,它们是否是std::function的合适的、性能良好的替代品?如果是这样,为什么std::function的实现方式不同?或者,不可能的快速C++代表有什么缺点? 编辑: 正如评论所要求的,“不可能的快速C++代表”的主要思想似乎是将指针存储到非类型化数据旁边,函数指针使用非指针类型的数据作为参数。“不可能的快速C++委托”扩展了以前的功能,以支持lambdas等。下面是“不可能的快速C++代表”中显示的代码摘要 类委托 { 公众: 代表() :对象_ptr(0) ,存根_ptr(0) {}
类委托
{
公众:
代表()
:对象_ptr(0)
,存根_ptr(0)
{}
模板
来自_方法的静态委托(T*object_ptr)
{
d代表;
d、 object_ptr=object_ptr;
d、 存根_ptr=&方法_存根;/#1
返回d;
}
void运算符()(int a1)常量
{
返回(*存根ptr)(对象ptr,a1);
}
私人:
typedef void(*存根类型)(void*对象ptr,int);
void*object\u ptr;
存根类型存根ptr;
模板
静态无效方法\u存根(无效*对象\u ptr,int a1)
{
T*p=静态投影(对象投影);
返回(p->*t方法)(a1);/#2
}
};
以下是两篇文章的链接:
<> P>不可能的快速C++代表有什么缺点吗?
仅提供示例句柄:
- 固定签名
(可以很容易地用模板固定)void(int)
- 方法指针(及其类)(因此不直接使用lambda/函子,也不使用常规函数指针)
操作符()
进行调整。
不确定处理函数指针的可能开销
提供的示例不处理:
- 所有权
std::function
的合适的性能替代品
如果你不需要所有权,可以
如果是这样,为什么std::function的实现方式不同
As
std::function
应该处理所有权问题。向我们展示这个概念。不要让我们去搜索那些实现是什么。它们是std::function的合适的、性能良好的替代方案吗?这实际上取决于用例std::function
是泛型的,因为它是一种库类型。当你必须非常通用时,你会失去一些性能。如果您的用例允许使用一种不太通用的方法,那么您可能可以使用自己的解决方案来压缩一些性能。真正的诀窍是,你能制作出一个更快的std::function
,它符合std::function
的所有要求。@NathanOliver速度惊人的委托怎么比std::function更不通用?IDK。你需要在这里展示。我不会去找它的。好吧,现在我看到了代码,至少我可以回答你的问题了。此委托不适用于非成员函数,因此它不是std::function
的替代品。
class delegate
{
public:
delegate()
: object_ptr(0)
, stub_ptr(0)
{}
template <class T, void (T::*TMethod)(int)>
static delegate from_method(T* object_ptr)
{
delegate d;
d.object_ptr = object_ptr;
d.stub_ptr = &method_stub<T, TMethod>; // #1
return d;
}
void operator()(int a1) const
{
return (*stub_ptr)(object_ptr, a1);
}
private:
typedef void (*stub_type)(void* object_ptr, int);
void* object_ptr;
stub_type stub_ptr;
template <class T, void (T::*TMethod)(int)>
static void method_stub(void* object_ptr, int a1)
{
T* p = static_cast<T*>(object_ptr);
return (p->*TMethod)(a1); // #2
}
};