C# 在 List 上的执行时间非常长.查找()

本文关键字:非常 执行时间 查找 List | 更新日期: 2023-09-27 18:32:10

我正在使用 C# 构建一个涉及基于网格的地图系统的游戏。我将网格系统存储在 List 对象中,其中 T 是包含位置和其他数据的类型。在调用查找磁贴邻居的函数时,我遇到了极端的执行延迟。我已经将延迟缩小到对我的列表的 Find() 方法的调用。该方法如下所示:

列表。查找(磁贴 => 磁贴。X == x && 瓷砖。Y == y)

为什么这会导致如此巨大的滞后?除了将磁贴存储在列表中之外,是否有更好的替代方法?

C# 在 List<T> 上的执行时间非常长.查找()

如果您的地图是正方形/矩形且大小固定(或可变大小但不经常更改),则通过使用二维数组并按索引访问切片,您可能会获得更好的性能。

您不指示x值和y值是切片索引还是与切片中包含的坐标相关。无论哪种方式,您都可以大概计算每个图块的索引,这样对于n图块,索引从 0..n-1 运行,可用于索引到数组中。

您可以将地图数组定义为:

Tiles[,] map = new Tiles[numXTiles, numYTiles];

然后,访问磁贴就像:

var tile = map[x, y];
有迹象表明,多维数组

的性能低于交错数组,但多维数组更容易创建,并且(在我看来)语法更好。如果这仍然是一个问题,您可以改用交错数组或使用一维数组,并将索引计算为:x + y * numXTiles .

Find是O(n),其中n是列表的计数。如果您总是按坐标对进行查找,字典确实会有所帮助,因为您可以在键上获得 O(1) 查找。您可以从Dictionary<Tuple<int,int>, Tile>开始,看看这是否适合您的需求。显然,从长远来看,字典是否更好取决于列表的大小和您需要执行的查找类型。

如果您经常执行相同类型的查询(如您的情况),则对组合键使用索引器来检索对象是有意义的,因为索引器通常具有或多或少恒定的性能。这意味着如果物体数量增加,找到物体的时间不会增加......

为此,请使用字典,其中 TKey 是一个字符串,每个键都是平铺。X + "" + 磁贴。以 Y 为例。要检索对象,只需调用 dic[tile。X + " + 磁贴。Y]

由于在该lambda表达式中,您暗示您知道x和y坐标,因此最好按照已经建议的方式使用2D数组。LINQ 很棒,但它不应该在任何地方使用。