std :: list问题 [英] std::list problem

查看:84
本文介绍了std :: list问题的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

这是我在codeproject.com上的第一篇帖子.对,我是游戏编程的新手,并且由于两个多小时的时间而陷入了这个问题.基本上,这是一个带有气泡和尖刺物体的小型2D游戏.我被困在需要检查碰撞的部分.我得到了可怕的迭代器无法引用错误.而且,它不会在循环的开始或结束时崩溃,它是相当随机的,因此我无法弄清在擦除列表中的元素时是否做错了什么.
在程序的开头,我实例化了这些类的对象.

This is my first post on codeproject.com Right I am new to game programming and I am stuck with this problem since more than two hours now. Basically it is a small 2D game with bubbles and spiky things. I am stuck with the part where I need to check the collisions. I am getting the dreaded iterator cannot be referenced error. Moreover, its not crashing at the beginning or end of the loop its pretty random and I am not able to figure out if I am doing something wrong while erasing the element from list.
in the beginning of the program I have instantiated objects of these classes.

Bubbles* bubbles;
Spikies* spikies;

这两个类分别具有std :: list气泡实例(bubbleList)和spiky实例(spikyList)

Both these classes have std::list of bubble instances( bubbleList)and spiky instances (spikyList) respectively

BubbleList::iterator bubbleIter;
SpikyList::iterator spikyIter;
bool isTouching = false;

bubbleIter = bubbles->bubbleList.begin();
if(!bubbles->bubbleList.empty())
{
    while( bubbleIter != bubbles->bubbleList.end() )
    {
        isTouching = false;
        for(spikyIter = spikies->spikyList.begin(); spikyIter != spikies->spikyList.end(); spikyIter++)
        {

            if( (*spikyIter)->mState == ALIVE)
                isTouching = (*bubbleIter)->boundingCircle->Intersects((*spikyIter)->boundingCircle);

            if(isTouching)
            {
                SAFE_DELETE(*bubbleIter);

                bubbleIter = bubbles->bubbleList.erase(bubbleIter);
                (*spikyIter)->mState = DEAD;


            }
        }
        //checking if we are not at the end of the list
        if( bubbleIter != bubbles->bubbleList.end())
            ++bubbleIter;
        //check if list is empty
        if( bubbles->bubbleList.empty() )
            break;
    }
}


任何输入将不胜感激.谢谢.


Any input would be much appreciated. Thanks.

推荐答案

您的逻辑与您想要的显示不符.您并没有按照自己的想法遍历这两个列表.一旦开始编写您的代码,我的工作就会比预期的要多.您将需要比较我与您自己所做的事情,并找出造成所有差异的原因.您还需要检查我所假设的意图是否正确. (而且,这已经超出了我的头脑,我还没有尝试过对其进行编译.)

Your logic isn''t right for what it appears you want to do. You are not iterating through the two lists the way that you think you are. Once I started in on your code, I ended up doing a bit more than I intended. You will want to compare what I did with your own and figure out the reason for all the differences. You will also want to check that what I am presuming your intent was is correct. (Also, this is off the top of my head, I haven''t tried compiling it.)

BubbleList::iterator bubbleIter;
SpikyList::iterator spikyIter;
bool isTouching = false;

bubbleIter = bubbles->bubbleList.begin();
while( bubbleIter != bubbles->bubbleList.end() )
{
    isTouching = false;
    for( spikyIter = spikies->spikyList.begin();
         spikyIter != spikies->spikyList.end();
         spikyIter++ )
    {
        if( (*spikyIter)->mState == ALIVE &&
            (*bubbleIter)->boundingCircle->Intersects((*spikyIter)->boundingCircle) )
        {
            isTouching = true;
            (*spikyIter)->mState = DEAD;
        }
    }
    if( isTouching  )
    {
        SAFE_DELETE(*bubbleIter);
        bubbleIter = bubbles->bubbleList.erase(bubbleIter);
    }
    else
        ++bubbleIter;
}



在对您的代码进行第二次查看时,我相信我已经发现了您报告的错误的直接来源.我上面的修订应该对此进行纠正.

请考虑这样一种情况,您在气泡列表的末尾有一个气泡,该气泡正在触摸一个不在尖峰列表末尾的尖峰.

在您原来的内部循环中,您将删除该气泡并将其从气泡列表中删除.这样,您可以将bubbleIter推进到bubbleList.end()-不再是实际的列表条目.由于您不在尖峰列表的末尾,因此您的内部循环将继续执行.它试图检查下一个尖刺是否正在接触现在由bubbleIter指示的气泡.但这不是气泡,而是bubbleList.end().您尝试访问它.繁荣!现在清除吗?您确实想提前终止内部循环,或者推迟删除气泡并推进bubbleIter,直到该循环结束之后.



At a second look over your code, I believe that I have spotted the immediate source of your reported error. It should be rectified by my revision above.

Consider the scenario that you have a bubble at the end of the bubble list that is touching a spiky that is not at the end of the spiky list.

In your original inner loop you will delete that bubble and remove it from the bubble list. In doing so, you advance your bubbleIter to bubbleList.end() - no longer an actual list entry. Since you are not at the end of the spiky list, your inner loop continues executing. It tries to check if the next spiky is touching the bubble now indicated by bubbleIter. But that is not a bubble, it is bubbleList.end(). You try to access it. Boom! Clear now? You really either wanted to terminate the inner loop early or defer deleting the bubble and advancing bubbleIter until after that loop finished.


尝试扩展您的步进条件:):
Try to extend your step condition :) :
if (!IsTouching && bubbleIter != bubbles->bubbleList.end()) {
  ++bubbleIter;
}


...还有这个范围" :):


...and this "scope" too :) :

if (isTouching)	{
  SAFE_DELETE(*bubbleIter);				
  bubbleIter = bubbles->bubbleList.erase(bubbleIter);
  (*spikyIter)->mState = DEAD;
  if (bubbleIter == bubbles->bubbleList.end()) {
    break; // there are no bubbles more :)
  }
}



请注意,现在只需触摸一下即可消除气泡,
所以只有一个刺刺者会被杀死... :)

Avi Berger 的代码答案确实显示了
如何用泡沫杀死所有感动的尖刺和
如何使程序更短,更容易,更安全和更易读:)

玩得开心!



Please note, that a bubble will be erased by the only one touching now,
so the only one spiky will be killed... :)

The code answer of Avi Berger does show
how to kill the all touched spikies by a bubble and
how to hold the procedure shorter, easier, more secure and readable :)

Have fun !


嘿Avi Berger,
非常感谢您的帖子.我的逻辑有问题...工作太晚会减慢逻辑思维的速度. :-D您的代码已解决它,但是对代码进行了一些小的修改.也许,我没有清楚地解释这个问题.我正在尝试破灭泡沫,并将尖峰标记为在嵌套循环中均已消失.在内部if语句中,我不得不跳出循环cos,循环仍然迭代检查与应该死的气泡的碰撞.所以这是更新.
干杯!:竖起大拇指:

Hey Avi Berger,
Thanks very much for the post. There was problem with my logic...working too late does slow down logical thinking. :-D Your code has resolved it but there is a small modification to the code. Perhaps, I did not explain the problem clearly. I am trying to burst the bubble and mark the spiky as dead both in the nested loops. In the inner if statement I had to break out of the loop cos the loop still iterates checking collisions with the bubble that is supposed to be dead. So here is the update.
Cheers!:thumbsup:

if( (*spikyIter)->mState == ALIVE &&
    (*bubbleIter)->boundingCircle->Intersects((*spikyIter)->boundingCircle) )
{
    isTouching = true;
    (*spikyIter)->mState = DEAD;
    break;//so that we dont check collision with the dead bubble again
}


这篇关于std :: list问题的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆