我应该在 Go 中以行主序还是列主序访问 2D 切片?
Should I access 2D slices in row major order or column major order in Go?
假设我有以下代码:
arr := make([][]byte, 10000)
for i := range arr {
arr[i] = make([]byte, 10000)
}
像这样遍历数组是否更快?
for row := len(arr) {
for col := len(arr[0]) {
// access arr[col][row]
}
}
或者像这样?
for col:= len(arr[0]) {
for row := len(arr) {
// access arr[col][row]
}
}
第二个版本允许执行较少的索引:您索引一次并获得一行。迭代一行可以通过仅索引“内部”切片来完成。
所以当遍历一片片时,总是先循环外片,你索引一次,然后你得到一个内片。您可以通过仅索引内部切片来迭代它(不需要总是索引外部切片)。
这也会导致顺序内存访问,这可能会导致编译器和运行时进一步优化。
所以这样做:
for _, row := range arr {
for _, value := range row {
// Use value
}
}
反其道而行之(当你首先增加内部切片的索引时),你总是必须使用双索引。
假设我有以下代码:
arr := make([][]byte, 10000)
for i := range arr {
arr[i] = make([]byte, 10000)
}
像这样遍历数组是否更快?
for row := len(arr) {
for col := len(arr[0]) {
// access arr[col][row]
}
}
或者像这样?
for col:= len(arr[0]) {
for row := len(arr) {
// access arr[col][row]
}
}
第二个版本允许执行较少的索引:您索引一次并获得一行。迭代一行可以通过仅索引“内部”切片来完成。
所以当遍历一片片时,总是先循环外片,你索引一次,然后你得到一个内片。您可以通过仅索引内部切片来迭代它(不需要总是索引外部切片)。
这也会导致顺序内存访问,这可能会导致编译器和运行时进一步优化。
所以这样做:
for _, row := range arr {
for _, value := range row {
// Use value
}
}
反其道而行之(当你首先增加内部切片的索引时),你总是必须使用双索引。