【问题标题】:Why does this string search and replace segfault?为什么这个字符串搜索和替换段错误?
【发布时间】:2011-01-01 21:15:27
【问题描述】:

coloursstd::map<string, string>,其中每对的第一个元素是 2 个字母的 std::string 颜色代码,第二个元素是该颜色的 7 个字符 std::string shell 转义代码。

size_t i;
for(map<string, string>::iterator iter = colours.begin(); iter != colours.end(); iter++) {
    while((i = text.find(iter->first)) != string::npos) {
        text.replace(i, i + sizeof(iter->first), iter->second);
    }
}

运行此代码时,程序会出现段错误。我最好的猜测是,这与替换字符串的长度比它要替换的字符串的长度长有关,但据我所知,这只会导致char * 的段错误,而不是std::string

【问题讨论】:

    标签: c++ string segmentation-fault


    【解决方案1】:

    string::replace 采用起始位置和长度,而不是起始位置和结束位置。 sizeof 也不返回字符串的长度。所以第三行可能应该是:

    text.replace(i, iter->first.length(), iter->second);
    

    对于它的价值,sizeof 返回对象消耗的 stack 空间量,这在编译时是已知的。所以它不会因调用而异,字符串的长度会有所不同。

    【讨论】:

    • 谢谢,我已经按照您的建议进行了更改,但程序仍然在此代码块上出现段错误。
    • @Not Joe Bloggs,嗯。在调试器中运行,找出究竟是什么条件导致它出现段错误?
    • @Not Joe Bloggs 你能给出导致段错误的输入吗?
    • 地图定义为pasted here,输入失败的示例为“{gtest{x”
    • 其实发现问题了。它与此代码位于同一函数的其他位置。
    【解决方案2】:

    @luqui 已经回答了它为什么会出现段错误,但我想添加其他内容。

    如果您的替换字符串包含搜索字符串,请注意不要陷入无限循环。您可以通过传递string::find() 一个位置来开始搜索来避免这种情况。这也将提高效率,因为您当前的解决方案可能会退化为 O(N2)。

    【讨论】:

    • 在这种情况下,搜索和替换字符串在编译时是已知的,所以我可以说替换字符串肯定不包含搜索字符串。
    猜你喜欢
    • 1970-01-01
    • 2018-01-02
    • 1970-01-01
    • 1970-01-01
    • 2015-10-03
    • 1970-01-01
    • 2020-01-06
    相关资源
    最近更新 更多