1

我有一个循环,应该检测并删除列表中与放置的对象相交的任何对象。代码如下:

for (int i = 0; i < levelObjects.Count(); i++)
{
    if (levelObjects[i].BoundingBox.Intersects(mouseBlock.BoundingBox))
    {
        levelObjects.RemoveAt(i);
    }
}

当遇到有多个碰撞的情况时,它有时检测不到碰撞。交集功能工作正常。我的循环是怎么回事?

4

4 回答 4

5

由于您要从循环中删除,因此您最终会跳过元素。更好的选择是向后循环:

for (int i=levelObjects.Count() - 1; i >= 0; --i)
{
  // ...

这可以防止您现在丢失的“跳过”对象,因为当您删除并且索引向下移动时,您只是在移动已经测试过的对象。

于 2013-01-15T22:29:20.237 回答
3

当您删除 index 处的对象时, indexi处的值会i + 1向下滑动到 index i。您的循环移动到 index i + 1,并且从不检查 index 处的新值i。您可以通过简单地向后循环来避免这种情况。

于 2013-01-15T22:29:10.363 回答
2

当您删除索引 i 处的 levelObject 时,您会将所有内容向下移动一个索引。因此,下一项现在位于索引 i 处。避免这种情况的一个简单方法是从最后开始并向后工作,即

for (int i = levelObjectsCount - 1; i >= 0; i--)
{
    if (levelObjects[i].BoundingBox.Intersects(mouseBlock.BoundingBox))
    {
        levelObjects.RemoveAt(i);
    }
}
于 2013-01-15T22:30:07.363 回答
1

您不能从您正在迭代的列表中删除!遍历副本或创建要删除的项目列表,然后再删除它们。示例(如果性能不是问题):

foreach (var obj in levelObjects.ToList())
{
    if (obj.BoundingBox.Intersects(mouseBlock.BoundingBox))
    {
        levelObjects.Remove(obj);
    }
}
于 2013-01-15T22:29:24.523 回答