c++字符串分割示例(类似于boost::split)

作者:袖梨 2022-06-25

由于c++字符串没有split函数,所以字符串分割单词的时候必须自己手写,也相当于自己实现一个split函数吧!

如果需要根据单一字符分割单词,直接用getline读取就好了,很简单

#include
#include
#include
#include
using namespace std;

int main()
{
    string words;
    vector results;
    getline(cin, words);
    istringstream ss(words);
    while (!ss.eof())
    {
        string word;
        getline(ss, word, ',');
        results.push_back(word);
    }
    for (auto item : results)
    {
        cout << item << " ";
    }
}

如果是多种字符分割,比如,。!等等,就需要自己写一个类似于split的函数了:

#include
#include
#include
#include
using namespace std;

vector is_any_of(string str)
{
    vector res;
    for (auto s : str)
        res.push_back(s);
    return res;
}

void split(vector& result, string str, vector delimiters)
{
    result.clear();
    auto start = 0;
    while (start < str.size())
    {
        //根据多个分割符分割
        auto itRes = str.find(delimiters[0], start);
        for (int i = 1; i < delimiters.size(); ++i)
        {
            auto it = str.find(delimiters[i],start);
            if (it < itRes)
                itRes = it;
        }
        if (itRes == string::npos)
        {
            result.push_back(str.substr(start, str.size() - start));
            break;
        }
        result.push_back(str.substr(start, itRes - start));
        start = itRes;
        ++start;
    }
}

int main()
{
    string words;
    vector result;
    getline(cin, words);
    split(result, words, is_any_of(", .?!"));
    for (auto item : result)
    {
        cout << item << ' ';
    }
}

例如:输入hello world!Welcome to my blog,thank you!

感谢@chxuan提供的另一种实现方法,使用strtok_s分割字符串:

std::vector split(const std::string& str, const std::string& delimiter)
{
    char* save = nullptr;
    char* token = strtok_s(const_cast(str.c_str()), delimiter.c_str(), &save);
    std::vector result;
    while (token != nullptr)
    {
        result.emplace_back(token);
        token = strtok_s(nullptr, delimiter.c_str(), &save);
    }
    return result;
}

用strtok函数进行字符串分割

原型: char *strtok(char *str, const char *delim);

功能:分解字符串为一组字符串。

参数说明:str为要分解的字符串,delim为分隔符字符串。

返回值:从str开头开始的一个个被分割的串。当没有被分割的串时则返回NULL。

其它:strtok函数线程不安全,可以使用strtok_r替代。

示例:

//借助strtok实现split
#include
#include

int main()
{
    char s[] = "Golden Global   View,disk * desk";
    const char *d = " ,*";
    char *p;
    p = strtok(s,d);
    while(p)
    {
        printf("%sn",p);
        p=strtok(NULL,d);
    }

    return 0;
}

运行效果如下图所示:

 

二、用STL进行字符串的分割

涉及到string类的两个函数find和substr:
1、find函数
原型:size_t find ( const string& str, size_t pos = 0 ) const;
功能:查找子字符串第一次出现的位置。
参数说明:str为子字符串,pos为初始查找位置。
返回值:找到的话返回第一次出现的位置,否则返回string::npos

2、substr函数
原型:string substr ( size_t pos = 0, size_t n = npos ) const;
功能:获得子字符串。
参数说明:pos为起始位置(默认为0),n为结束位置(默认为npos)
返回值:子字符串

实现如下:

//字符串分割函数
std::vector split(std::string str,std::string pattern)
{
  std::string::size_type pos;
  std::vector result;
  str+=pattern;//扩展字符串以方便操作
  int size=str.size();

  for(int i=0; i   {
    pos=str.find(pattern,i);
    if(pos     {
      std::string s=str.substr(i,pos-i);
      result.push_back(s);
      i=pos+pattern.size()-1;
    }
  }
  return result;
}

完整代码:

/*
    File   : split1.cpp
    Author  : Mike
    E-Mail  : [email protected]
 */
#include
#include
#include

//字符串分割函数
std::vector split(std::string str,std::string pattern)
{
  std::string::size_type pos;
  std::vector result;
  str+=pattern;//扩展字符串以方便操作
  int size=str.size();

  for(int i=0; i   {
    pos=str.find(pattern,i);
    if(pos     {
      std::string s=str.substr(i,pos-i);
      result.push_back(s);
      i=pos+pattern.size()-1;
    }
  }
  return result;
}

int main()
{
  std::string str;
  std::cout<<"Please input str:"<   //std::cin>>str;
  getline(std::cin,str);
  std::string pattern;
  std::cout<<"Please input pattern:"<   //std::cin>>pattern;
  getline(std::cin,pattern);//用于获取含空格的字符串
  std::vector result=split(str,pattern);
  std::cout<<"The result:"<   for(int i=0; i   {
    std::cout<   }

  std::cin.get();
  std::cin.get();
  return 0;
}

运行效果如下图所示:

 

三、用Boost进行字符串的分割

用boost库的正则表达式实现字符串分割
实现如下:

std::vector split(std::string str,std::string s)
{
    boost::regex reg(s.c_str());
    std::vector vec;
    boost::sregex_token_iterator it(str.begin(),str.end(),reg,-1);
    boost::sregex_token_iterator end;
    while(it!=end)
    {
        vec.push_back(*it++);
    }
    return vec;
}

完整代码:

//本程序实现的是利用正则表达式对字符串实现分割
//运行环境   VC6.0 + boost 库
/*
    File   : split2.cpp
    Author  : Mike
    E-Mail  : [email protected]
*/
#include
#include
#include
#include
#include "boost/regex.hpp"

std::vector split(std::string str,std::string s)
{
    boost::regex reg(s.c_str());
    std::vector vec;
    boost::sregex_token_iterator it(str.begin(),str.end(),reg,-1);
    boost::sregex_token_iterator end;
    while(it!=end)
    {
        vec.push_back(*it++);
    }
    return vec;
}
int main()
{
    std::string str,s;
    str="sss/ddd/ggg/hh";
    s="/";
    std::vector vec=split(str,s);
    for(int i=0,size=vec.size();i     {
        std::cout<     }
    std::cin.get();
    std::cin.get();
    return 0;
}

 

相关文章

精彩推荐