【发布时间】:2014-09-26 07:49:59
【问题描述】:
请考虑 GO 和 C++11 中的这两个 sn-ps。在 C++ 中,std::vector 是一个具有分期 O(1) 插入操作的加倍数组。如何在 GO 中达到同样的性能?问题是这个 GO 代码在我的硬件上慢了大约 3 倍。运行多次。
编译:
-
go build vec.go(去版本go1.2.1 linux/amd64) -
g++ -O2 -std=gnu++11 -o vec vec.cc(g++ (Ubuntu 4.8.2-19ubuntu1) 4.8.2)
GO 版本 (vec.go):
package main
type X struct {
x int32
y float64
}
const N int = 80000000
func main() {
x := X{123, 2.64}
s := make([]X, 1)
for i := 0; i < N; i++ {
s = append(s, x)
}
}
C++11 版本(vec.cc):
#include <vector>
const int N = 80000000;
struct X {
int x;
double y;
};
int main(void)
{
X x{123, 2.64};
std::vector<X> s(1);
for (int i = 0; i < N; ++i) {
s.push_back(x);
}
}
【问题讨论】:
-
我不懂 Go,但如果你关心性能,你的 C++ 代码应该在循环之前调用
reserve。 -
@jalf 不,我希望基准测试使用大小为 1 的相同初始数组。C++ 版本非常快。但是 Go 可能没有使用双数组算法。
-
当然,但是比较低效的代码和低效的代码并没有告诉你什么有用。这就像在没有启用优化的情况下进行编译。如果你想比较哪个更快,两个变体都应该写得很快。
-
@jalf 更改保留大小不会改变任何内容。您认为什么是低效的?
-
预先保留尺寸应该改变性能。它避免了重新分配内存和复制对象。这是摊销 O(1) 和 实际 O(1) 复杂度之间的差异。
标签: c++ performance c++11 vector go