STD Deque出奇地慢
std deque is surprisingly slow
我只是发现,与使用预分配数组的"自制"堆栈版本相比,标准标准 std deque 真的很慢。
这是我堆栈的代码:
template <class T>
class FastStack
{
public:
T* st;
int allocationSize;
int lastIndex;
public:
FastStack(int stackSize);
FastStack();
~FastStack();
inline void resize(int newSize);
inline void push(T x);
inline void pop();
inline T getAndRemove();
inline T getLast();
inline void clear();
};
template <class T>
FastStack<T>::FastStack()
{
lastIndex = -1;
st = NULL;
}
template <class T>
FastStack<T>::FastStack(int stackSize)
{
st = NULL;
this->allocationSize = stackSize;
st = new T[stackSize];
lastIndex = -1;
}
template <class T>
FastStack<T>::~FastStack()
{
delete [] st;
}
template <class T>
void FastStack<T>::clear()
{
lastIndex = -1;
}
template <class T>
T FastStack<T>::getLast()
{
return st[lastIndex];
}
template <class T>
T FastStack<T>::getAndRemove()
{
return st[lastIndex--];
}
template <class T>
void FastStack<T>::pop()
{
--lastIndex;
}
template <class T>
void FastStack<T>::push(T x)
{
st[++lastIndex] = x;
}
template <class T>
void FastStack<T>::resize(int newSize)
{
if (st != NULL)
delete [] st;
st = new T[newSize];
}
.
我运行这个简单的基准测试:
std::deque<int> aStack;
int x;
HRTimer timer;
timer.Start();
for (int i = 0; i < 2000000000; i++)
{
aStack.push_back(i);
x = aStack.back();
if (i % 100 == 0 && i != 0)
for (int j = 0; j < 100; j++)
aStack.pop_back();
}
double totalTime = timer.Stop();
stringstream ss;
ss << "std::deque " << totalTime;
log(ss.str());
.
使用带有矢量的 std 堆栈作为容器(如"Michael Kohne"所建议的那样)
std::stack<int, std::vector<int>> bStack;
int x;
HRTimer timer;
timer.Start();
for (int i = 0; i < 2000000000; i++)
{
bStack.push(i);
x = bStack.top();
if (i % 100 == 0 && i != 0)
for (int j = 0; j < 100; j++)
bStack.pop();
}
double totalTime = timer.Stop();
stringstream ss;
ss << "std::stack " << totalTime;
log(ss.str());
.
我的快速堆栈也是如此:
FastStack<int> fstack(200);
int x;
HRTimer timer;
timer.Start();
for (int i = 0; i < 2000000000; i++)
{
fstack.push(i);
x = fstack.getLast();
if (i % 100 == 0 && i != 0)
for (int j = 0; j < 100; j++)
fstack.pop();
}
double totalTime = timer.Stop();
stringstream ss;
ss << "FastStack " << totalTime;
log(ss.str());
.
4 次运行后的结果如下:
deque 15.529 deque 15.3756
deque 15.429
deque 15.4778
堆栈 6.19099 堆栈 6.1834
堆栈 6.19315
堆栈 6.19841
快速堆栈3.01085
快速堆栈 2.9934
快速堆栈 3.02536
快速堆栈 3.00937
结果以秒为单位,我在英特尔 i5 3570k(默认时钟)上运行代码。我使用了VS2010编译器和所有可用的优化。 我知道我的 FastStack 有很多限制,但有很多情况,它可以在哪里使用以及何时可以很好地提升!(我在一个项目中使用它,与 std::queue 相比,我的速度提高了 2 倍)。
所以现在我的问题是:
编辑:我不想冒犯,我只是好奇你是否知道一些未知的"加速"。
您正在比较苹果和橙子。取消排队是 DOUBLE-END,这要求它在内部与您实现的简单堆栈有很大不同。尝试针对std::stack<int, std::vector<int> >
运行基准测试,看看您是如何做到的。 std::stack 是一个容器适配器,如果您使用矢量作为底层容器,它应该与您自行开发的实现一样快。
一个缺点是 std::stack 实现没有办法让你预先设置大小,所以在你知道最大大小需要是多少的情况下,它最初会慢一点,因为它必须重新分配几次。在那之后,它将几乎相同。
如果您知道在任何给定时间堆栈中的最大元素数量,则应使用预先预留容量的std::vector
。即使您不知道容量,对于堆栈,您也应该使用会增长几倍的std::vector
(增长时成本高于预分配的向量),但永远不会收缩,因此一段时间后它将停止分配内存。
性能的问题在于,std::deque
会根据需要分配区块,并在不再需要时解除分配(遵循某种策略),因此,如果您经常填充和清除std::deque
就会不断进行分配和分配。
- 如何仅将新添加的元素复制到std :: Deque中
- 为什么STD :: Deque子阵列尺寸固定
- 为什么std::vector比std::deque更受欢迎
- STD Deque出奇地慢
- c++11移动std::deque或std::list的插入
- 将std::deque的现有元素推到前面
- 使用 std::stack 而不仅仅是 deque、vector 或 list 有什么优点和缺点
- C++std::从std::deque复制到std:;设置
- std::deque::erase函数的时间复杂度是多少
- 如何在Visual studio 2010中查看存储在std::deque中的内容(调试模式)
- 类的const成员出现std::deque::erase编译错误
- 'deque itrator not dereferencable' 而做 std::d eque->front()
- 对std::deque执行迭代器在容器两端插入或擦除后会失效
- 一个线程读一个线程写,std::deque是安全的
- std::deque::push_back/front的复杂度要求
- c++ std::deque实现:为什么不使用循环缓冲区
- 为什么std::deque的效率这么差?
- 为什么std::deque在默认构造函数中为它的元素分配内存?
- Bug with std::deque?
- 如何获取指向原始数据的std::deque指针