[英]C/C++: Is there a performance penalty for using the adapter pattern?
我在C ++项目中使用C语言编写的高性能/并行图形库 。 它提供了结构stinger
(图形数据结构)和操作之类的
int stinger_insert_edge_pair (struct stinger *G,
int64_t type, int64_t from, int64_t to,
double weight, int64_t timestamp) { .... }
但是,大多数情况下,我不想指定时间戳或权重或类型。 默认参数会很好。 此外,类似OOP的界面会很好: G->insertEdge(u, v)
而不是insert_edge_pair(G, u, v, ...)
。
所以我在考虑创建一个类似的适配器类
class Graph {
protected:
stinger* stingerG;
public:
/** default parameters ***/
double defaultEdgeWeight = 1.0;
/** methods **/
Graph(stinger* stingerG);
virtual void insertEdge(node u, node v, double weight=defaultEdgeWeight);
};
insertEdge(...)
方法只需使用适当的参数调用stinger_insert_edge_pair(this->stingerG, ...)
。
但是,性能是一个至关重要的方面。 使用这样的适配器类有什么性能损失? 与使用“裸”库相比,我是否应该期望性能下降?
虚函数通常不能内联,因此函数调用会产生相同的开销(推送堆栈上的参数,可能会中断管道和缓存等)。 实际上,例程函数调用非常快 - 按时钟周期排序。 确定这是否合适的唯一方法是测试您自己的应用程序。
如果你使用普通的inline
方法,编译器应该在调用点内联它们,这样就不会有任何性能损失。 但请注意,您不应该使用虚函数。
如果你的insertEgde只是将调用转发给stinger_insert_edge_pair,那么(很可能)在对stinger_insert_edge_pair和g-> insertEdge的普通调用之间生成的代码没有区别(前提是你删除了虚拟指定符)。 比较通过普通调用和适配器调用生成的汇编代码可以为您的适配器带来的开销提供公平的输入。
insertEdge必须是虚拟的吗? 你打算有Graph的子类吗? 但同样,与功能执行本身的实际成本相比,虚函数调用的成本几乎可以忽略不计。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.