在c ++中基于多个字符串分隔符分割字符串?

内容来源于 Stack Overflow,并遵循CC BY-SA 3.0许可协议进行翻译与使用

  • 回答 (1)
  • 关注 (0)
  • 查看 (118)

我只使用标准库在C ++ 98中编写我的代码。我试图编写一些代码来分割一个字符串在多个子字符串中,每个字符串由字符串“OK”或字符串“ERROR”分隔。每个子字符串应放在mysubstring数组中。

这是我为单个分隔符编写的代码:

void split_string()
{
   for (unsigned short k=0;k<10;k++)
   {
      mysubstring[k]=""; //resetting all substrings
   }
   string separator = "OK";
   size_t pos = 0;
   unsigned short index=0;
   while ((pos = str_to_split.find(separator)) != std::string::npos) {
   mysubstring[index] = str_to_split.substr(0, pos);
   str_to_split.erase(0, pos + separator.length());
   index++;
}

这个单独的分隔符版本工作正常 然后我尝试升级到两个分隔符:

    void split_string()
    {
        for (unsigned short k=0;k<10;k++)
        {
            mysubstring[k]=""; //resetting all substrings
        }
        string okseparator = "OK";
        string koseparator = "ERROR";
        size_t  okpos = 0;
        size_t  kopos = 0;
        unsigned short index=0;
        while ((okpos = string_to_split.find(okseparator)) != std::string::npos)
       {
        while ((kopos = string_to_split.find(koseparator)) != std::string::npos)
          {
            if (okpos <= kopos)
            {
               mysubtring[index] = string_to_split.substr(0, okpos + okseparator.length());

               string_to_split.erase(0, okpos + okseparator.length());
               index++;
            }
            else
            {
                mysubstring[index] = string_to_split.substr(0, kopos + koseparator.length());
                string_to_split.erase(0, kopos + koseparator.length());
                index++;
            }
        }
    }

        while ((kopos = string_to_split.find(koseparator)) != std::string::npos)
        {
            mysubtring[index] = string_to_split.substr(0, kopos + koseparator.length());
            string_to_split.erase(0, kopos + koseparator.length());
            index++;
            }
}

这里的想法是,我留在第一个while循环,直到所有“OK”消耗完,然后它进入最后一个时刻,结束所有“ERROR”。子串应该按照它们在string_to_split原始字符串中的顺序输入mysubstring数组。

测试和验证示例:

#include <iostream>
#include <string.h>

void split_string();

string str_to_split = "skdjfnsdjknfjk OK    fkjsnfjksdnfjnsdjkfn ERROR skjdfnjksdnf OK sjkdnfjksdnfjERROR jnfjnsdjfnsjdknfjkn       OK";

use namespace std;
int main()
{
  split_string();
  return 0;
}
提问于
用户回答回答于

一个非常原始的例子:

#include <iostream>
#include <vector>
#include <string>
#include <cstring>


void print_tokens(const std::vector<std::string>& tokens)
{
    for(std::vector<std::string>::const_iterator it = tokens.cbegin(); it != tokens.cend(); ++it)
        std::cout << *it << ' ';
    std::cout << std::endl;
}

int main()
{
    //std::string to_split = "AAAOKBBEBEBERERRORCCCOK";
    std::string to_split = "skdjfnsdjknfjk OK    fkjsnfjksdnfjnsdjkfn ERROR skjdfnjksdnf OK sjkdnfjksdnfjERROR jnfjnsdjfnsjdknfjkn       OK";

    std::vector<std::string> ok_tokens;
    std::vector<std::string> error_tokens;

    const unsigned short OK_TOK = ('O' << 8) | 'K';
    const unsigned short ER_TOK = ('E' << 8) | 'R';

    std::string::iterator  s = to_split.begin();
    unsigned short lex = *s;
    std::string token;

    while(to_split.end() != s) {
        lex = lex << 8 | *s;
        switch(lex) {
        case OK_TOK:
            if(!token.empty()) {
                ok_tokens.push_back( std::string( token.begin(), token.end() - 1)  );
                token.clear();
            }
            ++s;
            continue;
        case ER_TOK:
            if( std::string(s-1, s+4) == "ERROR"  && !token.empty()) {
                error_tokens.push_back( std::string( token.begin(), token.end() - 1) );
                token.clear();
                s += 4;
            }
            continue;
        }
        token.push_back( *s );
        ++s;
    }
    std::cout << "OK tokens: \n \t";
    print_tokens(ok_tokens);
    std::cout << "ERROR tokens: \n \t";
    print_tokens(error_tokens);
    std::cout.flush();

    return 0;
}

扫码关注云+社区

领取腾讯云代金券