我在第8行遇到了运行时错误“map / set iterators incompatible”。
void Manager::Simulate(Military* military, Shalishut* shalishut,char* args[]){
Simulation* simulation = Simulation::GetInstance();
Time* time = Time::GetInstance();
multimap<int,Task*>::iterator itTasks;
itTasks = simulation->GetTasks().begin();
while(itTasks != simulation->GetTasks().end()){
while (itTasks->second->GetTimeStamp() == time->GetTime()){ /*line 8 - ERROR*/
TaskExecute(itTasks->second,military,shalishut,args);
itTasks++;
}
// Unit take car of vehicles
time->TimeIncrease();
}
}
Simulation
被声明为multimap<int,Task*>
。有什么问题?
答案 0 :(得分:18)
我会猜测并说Simulation::GetTasks()
签名如下:
multimap<int,Task*> GetTasks() const;
每次调用时都会创建一个新的多图(副本)。
比较迭代器时,两个multimap<int,Task*>
迭代器必须来自同一个容器;由于每次拨打GetTasks()
时都会收到新副本,因此违反了此约束,这就是您的错误来源。您还有另一个问题 - 临时多图副本在创建它们的语句后被销毁,因此您的迭代器会立即失效。
你有两个选择;一种是在本地捕获副本并始终如一地使用该副本:
multimap<int,Task*> tasks = simulation->GetTasks();
multimap<int,Task*>::iterator itTasks;
itTasks = tasks.begin();
while(itTasks != tasks.end()){
while (itTasks->second->GetTimeStamp() == time->GetTime()){
TaskExecute(itTasks->second,military,shalishut,args);
itTasks++;
}
// Unit take car of vehicles
time->TimeIncrease();
}
另一种方法是让GetTasks()
返回对持久性多图的引用,确保每次使用相同的一个:
multimap<int,Task*> &GetTasks();
或const引用:
const multimap<int,Task*> &GetTasks() const;
这样做的好处是可以避免复制multimap
的(可能很大)开销。
请注意,使用const引用需要使用const_iterator
来逐步执行多重映射。我建议定义const和非const访问器(如果Simulation
指针或引用是const,C ++将选择正确的访问器),除非你想要完全禁止直接修改底层multimap
,在这种情况下,您只能定义const
变体。