我一直在试图说服我的一个朋友避免使用动态分配的数组,并开始转向STL向量。我给他发了一些示例代码,展示了可以使用STL和functors/生成器完成的一些事情:
#include <iostream>
#include <vector>
#include <algorithm>
#include <iterator>
#define EVENTS 10000000
struct random_double {
double operator() () { return (double)rand()/RAND_MAX; }
};
int main(int argc, char **argv){
std::vector<double> vd (EVENTS);
generate(vd.begin(), vd.end(), random_double());
copy(vd.begin(), vd.end(), std::ostream_iterator<double>(std::cout, "\n"));
return 0;
}
他的回答是,尽管他觉得更优雅,但他自己的代码更快(几乎快了2倍!)下面是他回复的C代码:
#include <stdio.h>
#include <stdlib.h>
#include <malloc.h>
#include <string.h>
#define EVENTS 10000000
__inline double random_double() {
return (double)rand()/RAND_MAX;
}
int main(int argc, char **argv){
unsigned int i;
double *vd;
vd = (double *) malloc(EVENTS*sizeof(double));
for(i=0;i<EVENTS;i++){ vd[i]=random_double(); }
for(i=0;i<EVENTS;i++){ printf("%lf\n",vd[i]); }
free(vd);
return 0;
}
所以我运行了一个简单的计时测试,看看会发生什么,下面是我得到的结果:
> time ./c++test > /dev/null
real 0m14.665s
user 0m14.577s
sys 0m0.092s
> time ./ctest > /dev/null
real 0m8.070s
user 0m8.001s
sys 0m0.072s
使用g++的编译器选项是: g++ -finline -funroll-loops。没什么特别的。谁能告诉我为什么在这种情况下C++/STL版本比较慢?瓶颈在哪里,我能说服我的朋友使用STL容器吗?
发布于 2009-12-19 03:15:39
使用printf:
for (std::vector<double>::iterator i = vd.begin(); i != vd.end(); ++i)
printf("%lf\n", *i);
结果是:
koper@elisha ~/b $ time ./cpp > /dev/null
real 0m4.985s
user 0m4.930s
sys 0m0.050s
koper@elisha ~/b $ time ./c > /dev/null
real 0m4.973s
user 0m4.920s
sys 0m0.050s
使用的标志:-O2 -funroll-loops -finline
发布于 2009-12-19 03:05:40
几乎可以肯定的是,使用iostream库还是使用printf()。如果你想给算法计时,你应该在循环之外输出。
发布于 2009-12-19 03:06:44
使用STL,特别是在使用向量和其他很好的实用类时,可能总是比使用malloc和内联函数的手写C代码慢。没有真正的方法可以绕过它。
话虽如此,但性能并不代表一切--也不是那么简单。使用STL还提供了许多其他好处,包括:
你实际上是在试图争论在更高的抽象级别上工作-这里有权衡,通常是在性能方面,但有一个原因,几乎所有的开发都到了更高的抽象级别;在大多数情况下,收益比牺牲要有价值得多。
https://stackoverflow.com/questions/1930081
复制相似问题