我有一个定制的环形缓冲区实现,它使用通过 new []
分配的普通数组,然后使用 std::move
将元素移入数组。这是我的 push()
方法的实现:
void push(value_type&& value)
{
_content[_end] = std::move(value); // 9.2% of execution is spend here
increment(); // 0.6% here
}
我正在向数组中移动的对象基本上只是一个指针和一个std::unique_ptr
:
struct Task
{
Task()
{}
Function function;
Batch *batch;
};
函数的格式如下:
function
class Function
{
public:
template<typename F>
Function(F&& f) :
_implementation(new ImplementationType<F>(std::move(f)))
{}
void operator() () { _implementation->Call(); }
Function() = default;
Function(Function&& other) :
_implementation(std::move(other._implementation))
{}
Function& operator=(Function&& other)
{
_implementation = std::move(other._implementation);
return *this;
}
Function(const Function&) = delete;
Function(Function&) = delete;
Function& operator= (const Function&) = delete;
private:
struct Base
{
virtual void Call() = 0;
virtual ~Base() {}
};
template<typename F>
struct ImplementationType : Base
{
ImplementationType(F&& f) :
function(std::move(f))
{}
void Call()
{
function();
}
F function;
};
std::unique_ptr<Base> _implementation;
};
我在循环中重复调用环形缓冲区的push()
方法,以填充任务缓冲区,这里没有其他计算。我期望std::move()
的开销非常小,绝对不会占用大部分计算时间。有人能指导我我做错了什么吗?
std::move
调用生效。 - R. Martinho FernandesInstruments
附加到程序中,并捕获了大约两分钟的运行时间。它标记了我将数据移入数组的那一行,占用了9.2%的执行时间(如注释中所示)。使用最新的Xcode 5附带的Clang编译,使用-Os
选项,没有调试信息或运行时断言。 - JustSidstd::move
,而是你对象的移动构造函数。我不确定你在这里期望什么:如果你只是把东西放进缓冲区,那么把东西放进缓冲区(即移动它)将是最常见的活动。 - R. Martinho Fernandesstd::move
只是一个编译时转换,不会生成任何运行时代码。更准确地说,std::move(value)
等同于static_cast<value_type&&>(value)
。它在运行时不会产生任何开销。 - Cassio Neri_content[_end]
不为空,则分配唯一指针将删除旧对象。也许这就是花费时间的原因? - Mike Seymour