目标 我正在构建一个世界生成器,当相机接近已经存在的边缘时,它应该能够动态地将“体素”添加到某种列表中。每个体素应该尽可能高效地访问,因为每帧需要访问来自数千个列表的几百个体素。
我考虑过的方法
1)我的第一个想法是体素的多维数组,它的索引是体素的x和y坐标:Voxels[,] voxels = new Voxel[128,128];
优点:假设我知道我的体素的坐标:Voxel myVoxel = voxels[x, y];
,这应该非常快
缺点:我要么限制世界大小,要么每次我想要生成新的地形时我必须完全重新创建数组...
2)为了解决这个问题,我想我可以将x和y值存储在一个字符串中,并将它们用作字典中的键。 Dictionary<string, Voxel> voxels = new Dictionary<string, Voxel>();
Voxel myVoxel = voxels[x + "," + y];
然后添加到列表就像调用.Add();方法。
质询 1)从数组中提取的效率与字典有何不同。在我的脑海中,一个数组会更快,因为我假设字典必须遍历每个键以检查相等性(如果我错了,请原谅我的无知)
2)如果一个数组真的要快得多,那么每秒多次(取决于块大小)会破坏并重新创建数十万个项目的数组值得吗?
请注意,目标平台是手机,并不是每个生成的体素都会存储在ram中,因此列表永远不会变得非常危险。仍然需要进行测试以确定具体尺寸,但概念是......
提前致谢
对于你的问题,
1)如果您知道数组中元素的索引,则数组最快(O(1)时间)。例如,如果您正在使用世界位置,则可以使用每个体素的世界位置坐标的楼层作为3D阵列中的索引。基本上,当您从3D数组生成世界时,使用索引作为世界位置,然后您将能够在3D数组中使用Math.floor(worldPosition)在恒定时间内找到它们的索引 - 这是最快的。
当您在不知道索引的情况下搜索未排序的数据结构时,字典比数组更快。有关图片,请参阅here(未排序列表的字典查找为O(1),数组查找为O(n))。
2)您可能需要使用多线程才能运行良好。例如,您可以使用不同的线程为3D阵列的每个四分之一生成数据,然后将线程与主线程连接起来以生成对象。只要在使用主线程加入线程后生成对象并且仅使用其他线程生成3D数组(如果您使用Unity,那么)不应该遇到此方法的问题你不能在其他线程中使用任何Unity库函数)。
此外,如果您使用Unity https://www.youtube.com/watch?v=wbpMiKiSKm8&list=PLFt_AvWsXl0eBW2EiBtl_sxmDtSgZBxB3,我强烈建议您查看Sebastian Lague关于地形生成的视频,了解其他最佳做法