简体   繁体   English

需要帮助在C ++中擦除和插入

[英]Need help erasing and inserting in C++

So basically I want to create a format function that accepts a string, and replaces words in that string with whatever the user wants to be replaced. 因此,基本上我想创建一个接受字符串的格式函数,并用用户要替换的内容替换该字符串中的单词。 At first I had some issues with non-deferencable iterators until I realized that when you change the the size of a string you can invalid any iterators. 刚开始,我遇到了一些不可延期的迭代器的问题,直到我意识到更改字符串的大小可以使任何迭代器无效。 It doesn't throw anymore exceptions now now the output is the same as the input. 现在,它的输出与输入相同,不再抛出异常。 Any advice??? 有什么建议吗?

string& formatFn(string& s, string& oldWord, string& newWord)
{
    string word = "";
    for (auto iter1 = s.begin(); iter1 != s.end(); ++iter1)
    {       
            string tmpWord = "";                         
        if (!isblank(*iter1))       // Testing for whitespace
        {
            tmpWord += *iter1;
            if (tmpWord == oldWord)
            {
                string::iterator beg = iter1 - word.size();
                string::iterator end = iter1;
                auto sIter = s.erase(beg, end);                 // Get the position returned by erase
                auto i = sIter - s.begin();                     // Get an index 
                s = s.insert(s[i], newWord);
            }
        }
        if (isblank(*iter1))
        {
            tmpWord.clear();
        }
    }
    return s;
}
string::iterator beg = iter1 - word.size();

I'm not sure what word actually does. 我不确定实际上是做什么word You are trying to delete oldWord , right? 您正在尝试删除oldWord ,对吗? Then it should be: 然后应该是:

string::iterator beg = iter1 - oldWord.size();

EDIT : This is an improved version of your code: 编辑:这是您的代码的改进的版本:

string formatFn(const string& s, const string& oldWord, const string& newWord) {
    string result = "";     // holds the string we want to return
    string word = "";       // while iterating over 's', holds the current word

    for (auto iter1 = s.begin(); iter1 != s.end(); ++iter1)  {       
        if (!isblank(*iter1))
            word += *iter1;
        else {    // if it is a whitespace, it must be the end of some word
            // if 'word' is not same as 'oldword', just append it
            // otherwise append 'newWord' instead

            if (word == oldWord)
                result += newWord;
            else
                result += word;
            result += *iter1;
            word.clear();    // reset 'word' to hold the next word in s
        }
    }

    // the end of the string might not end with a whitespace, so the last word
    // might be skipped if you don't make this test

    if (word == oldWord)
        result += newWord;
    else
        result += word;

    return result;
}

If you already use string why don`t use all methods? 如果您已经使用了字符串,为什么不使用所有方法呢?

for (auto it = text.find(o_text); it != string::npos; it = text.find(o_text)){
    text.replace(it, o_text.size(), n_text);
}

You are over-complicating it: 您过于复杂了:

std::string replace_all(std::string s, const std::string& sOld, const std::string& sNew)
{
    std::size_t p = s.find(sOld);
    while (p != std::string::npos)
    {
        s.replace(p, sOld.length(), sNew);
        p = s.find(sOld, p + sNew.length());
    }
    return s;
}

If you are looking to replace whole words only (which your current attempt will not do): 如果您只想替换整个单词(您当前的尝试不会这样做):

#include <iostream>
#include <string>

bool test(const std::string& s, const std::string& sOld, std::size_t pos)
{
    return (pos == 0 || !::isalpha(s[pos - 1])) && (!::isalpha(s[pos + sOld.length()]) || pos + sOld.length() >= s.length());
}

std::size_t find_word(const std::string& s, const std::string& sOld, std::size_t pos)
{
    pos = s.find(sOld, pos);
    while (pos != std::string::npos && (!test(s, sOld, pos) && pos < s.length()))
    {
        pos++;
        pos = s.find(sOld, pos);
    }
    return pos;
}

std::string replace_all(std::string s, const std::string& sOld, const std::string& sNew)
{
    std::size_t p = find_word(s, sOld, 0);
    while (p != std::string::npos && p < s.length()) 
    {
        s.replace(p, sOld.length(), sNew);
        p = find_word(s, sOld, p + sNew.length()); 
    }
    return s;
}

int main() 
{
    std::string sOrig = "eat Heat eat beat sweat cheat eat";
    std::string sOld = "eat";
    std::string sNew = "ate";
    std::string sResult = replace_all(sOrig, sOld, sNew);
    std::cout << "Result:  " << sResult << std::endl;
    // Output:  "ate Heat ate beat sweat cheat ate"
    return 0;
}

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM