取消引用set迭代器会导致seg错误

时间:2014-08-03 02:50:14

标签: c++ segmentation-fault

我正在尝试确定以下代码为什么在第10行(我们取消引用upgradeIter)中抛出段错误。

bool UpgradeType::isAffected(const UnitType *unitType) const{
    if(std::find(effects.begin(), effects.end(), unitType)!=effects.end()) return true;

    // Check if the unit has any of the affected tags
    std::set<string>::iterator upgradeIter;
    for(upgradeIter = tags.begin(); upgradeIter != tags.end(); ++upgradeIter) {
        std::set<string>::iterator unitIter;
        for(unitIter = unitType->getTags().begin(); unitIter != unitType->getTags().end(); ++unitIter) {
            string unitTag = *unitIter;
            string upgradeTag = *upgradeIter;
            if(unitTag == upgradeTag) return true;
        }
    }

    return false;
}

上下文是UpgradeType有“标签”(只是一组字符串)。单位也有标签。如果一个单元与升级共享至少一个标签,则该单元会受到升级的影响。

我认为没有任何理由说明上述行会崩溃。在我看来,没有任何情况下迭代器可能无效。

在显示tags内容的代码的其他部分(以非常类似的方式使用)中,输出符合预期。

编辑:我刚刚发现unitType->getTags().size()为0.所以我不明白为什么for循环的主体被执行了。但是,unitIter != unitType->getTags().end()正在评估为真。这似乎是关闭。

1 个答案:

答案 0 :(得分:0)

我设法在Yggdrasil on this site的帮助下找到了解决方案(这也意味着Matt McNabb在问题的评论中是正确的)。引用他的帖子如下:

  

正如在stackoverflow上或多或少提到的那样:更改getTags()以返回引用,而不是值/副本。

     

const set &getTags() const {return tags;}

     

请注意返回类型是const,因此请使用const迭代器。

     

不确定是否全部,但你肯定不想在那里(深)复制。迭代器超出范围,因为您检查不同集的末尾。每次调用getTags()都会获得自己的副本。