【发布时间】:2014-04-29 17:57:50
【问题描述】:
忽略很多细节:
假设我有一个包含函数的抽象 Card 类:
virtual int getType()=0;
由同样抽象的GreenCard 派生,其中有一个
virtual int getType()=0;
也是。
那么GreenCard是由定义纯虚的非抽象Follower和Item派生的:
int getType(){ return 1;}
在 Follower 类中和
int getType(){ return 2;}
在 Item 类中。
稍后我创建(并填写)GreenCard 指针列表
list<GreenCard*>* hand;
...我想循环打印手牌(取决于它们的类型):
list<GreenCard *>::iterator it;
for(it=hand->begin() ; it!=hand->end() ; ++i){
tp.getCorrectType(*it);
...
}
在这个函数中,我在第一行得到了 SegFault!
void getCorrectType(GreenCard* card)
{
/*SF here->*/ if(card->getType()==2){
...
}
}
我确信“卡”已正确创建和初始化,因为在上一行我在 gdb 中写入:p *card ...我可以看到它的所有字段(卡、绿卡和与项目相关的字段——是的,它是一个“项目”)都正确!
编辑:好的,那么这里有更多代码:
class Player{
list<GreenCard*>* fateDeck;
list<GreenCard*>* hand;
static const int START_HAND = 4;
Player(){
fateDeck = new list<GreenCard*> ();
hand = new list<GreenCard*>();
}
void initialize(){
DeckBuilder db;
*fateDeck = *(db.createFateDeck() );
db.deckShuffler(fateDeck);
initializeHand();
}
void initializeHand(){
for(int counter=0 ; counter<START_HAND ; counter++){
drawFateCard();
}
void drawFateCard(){
hand->push_front(fateDeck->front());
fateDeck->pop_front();
cout<<'\n'<<"Drawing from fate deck..."<<'\n'<<endl;
}
void Player::printHand(){
TypeConverter tp;
list<GreenCard *>::iterator it;
cout<<"You have " << hand->size()<<" fate cards in hand"<<'\n'
<<"They are the following:"<<endl;
for(it=hand->begin() ; it!=hand->end() ; ++it){
tp.getCorrectType(*it);
// printing depending on type
}
}
void startingPhase(){
printHand();
}
}
class DeckBuilder
{
private:
list<GreenCard*>* green;
public:
DeckBuilder();
list<GreenCard *>* createFateDeck();
void deckShuffler(list<GreenCard*>* green);
};
DeckBuilder :: DeckBuilder()
{
green = new list<GreenCard*>();
srand ( unsigned ( time (NULL) ) );
}
list<GreenCard *>* DeckBuilder :: createFateDeck()
{
int i;
for(i=0;i<40;i++) green->push_back(new Follower());
return green;
}
void DeckBuilder :: deckShuffler(list<GreenCard*>* green)
{
vector<GreenCard *> vect;
list<GreenCard*> ::iterator it;
for(it = green->begin();it!=green->end();it++)
vect.push_back((*it));
random_shuffle ( vect.begin(), vect.end() );
green->clear();
vector<GreenCard*>:: iterator it2;
for(it2 = vect.begin();it2!=vect.end();it2++)
green->push_back((*it2));
}
最终在 main() 中
Player pl();
pl.initialize();
pl.startingPhase;
以及 printHand() 中的段错误;
【问题讨论】:
-
你能在你填写列表的地方显示代码吗?以及分段错误输出?
-
同上。看起来列表中的指针变坏了。您是否可以选择使用智能指针(例如 shared_ptr)而不是原始指针?另外,你没有说
tp.getCorrectType()中的tp是什么... -
您可能已经删除了列表指向的对象,但您还没有发布填充列表的代码,这可能是您的问题的根源。该对象可能已被删除,这会在您稍后访问该对象时产生 SIGSEV。
-
也许;或者也许内存已被释放,只是没有其他任何东西覆盖它。我不确切知道您的调试器在这种情况下的行为。
-
@user2409839 - 那么您希望 SO 如何帮助您?你声称你所做的一切都不是错的,但有些事情是错的。我们只有您发布的一个循环,显示有效的 C++ 代码和一个函数调用。这真的没有帮助。
Me and my coworker have searched really deep and still cannot justify this segfault, any ideas why this is happening??这是错误的结论。 每一次崩溃都是有道理的。您只是没有找到崩溃发生的原因。
标签: c++ segmentation-fault polymorphism virtual invocation