我在D中有一个静态三维数组,通常是
Struct[WIDTH][HEIGHT][DEPTH] values;
其中两个维度成千上万。如果我想迭代遍历这个数组线性访问内存位置,那么哪个维度应该在外部循环中迭代? WIDTH
或DEPTH
?
答案 0 :(得分:4)
外部循环应为DEPTH
,如以下程序所示:
import std.stdio;
void main() {
enum X = 6, Y = 4, Z = 2;
ubyte[X][Y][Z] root;
foreach (i, ref level3; root) {
foreach (j, ref level2; level3) {
foreach (k, ref level1; level2) {
writefln("%s %s %s: 0x%x", i, j, k, &level1);
}
}
}
}
打印:
0 0 0: 0x7fbfc8b9f0
0 0 1: 0x7fbfc8b9f1
0 0 2: 0x7fbfc8b9f2
0 0 3: 0x7fbfc8b9f3
0 0 4: 0x7fbfc8b9f4
0 0 5: 0x7fbfc8b9f5
0 1 0: 0x7fbfc8b9f6
0 1 1: 0x7fbfc8b9f7
0 1 2: 0x7fbfc8b9f8
0 1 3: 0x7fbfc8b9f9
0 1 4: 0x7fbfc8b9fa
0 1 5: 0x7fbfc8b9fb
0 2 0: 0x7fbfc8b9fc
0 2 1: 0x7fbfc8b9fd
0 2 2: 0x7fbfc8b9fe
0 2 3: 0x7fbfc8b9ff
0 2 4: 0x7fbfc8ba00
0 2 5: 0x7fbfc8ba01
0 3 0: 0x7fbfc8ba02
0 3 1: 0x7fbfc8ba03
0 3 2: 0x7fbfc8ba04
0 3 3: 0x7fbfc8ba05
0 3 4: 0x7fbfc8ba06
0 3 5: 0x7fbfc8ba07
1 0 0: 0x7fbfc8ba08
1 0 1: 0x7fbfc8ba09
1 0 2: 0x7fbfc8ba0a
1 0 3: 0x7fbfc8ba0b
1 0 4: 0x7fbfc8ba0c
1 0 5: 0x7fbfc8ba0d
1 1 0: 0x7fbfc8ba0e
1 1 1: 0x7fbfc8ba0f
1 1 2: 0x7fbfc8ba10
1 1 3: 0x7fbfc8ba11
1 1 4: 0x7fbfc8ba12
1 1 5: 0x7fbfc8ba13
1 2 0: 0x7fbfc8ba14
1 2 1: 0x7fbfc8ba15
1 2 2: 0x7fbfc8ba16
1 2 3: 0x7fbfc8ba17
1 2 4: 0x7fbfc8ba18
1 2 5: 0x7fbfc8ba19
1 3 0: 0x7fbfc8ba1a
1 3 1: 0x7fbfc8ba1b
1 3 2: 0x7fbfc8ba1c
1 3 3: 0x7fbfc8ba1d
1 3 4: 0x7fbfc8ba1e
1 3 5: 0x7fbfc8ba1f
请注意,地址以线性方式增加,而最快变化的索引为X
。因此内部循环代表X
,外部循环代表Z
。
答案 1 :(得分:3)
yaz'的回答非常好。但是为了记住语义,可能有助于将数组声明视为“左关联” - 也就是说,ubyte value[X][Y]
声明了
(元素类型的长度为Y的数组(元素类型的长度为X的数组(ubyte)))
或(((ubyte value)[X])[Y])
。
答案 2 :(得分:0)
我相信所有D编译器都会在优化过程中自动展开。至少这是有人在IRC上传递给我的未经证实的信息。
逻辑上,第一个循环应该是您知道不会有很多值的维度。内部循环应该是你提到的那些尺寸将成千上万。