C++中string字符串分割函数split()的4种实现方法

目录
  • 一、使用stringstream流
  • 二、使用string类提供的find方法与substr方法
  • 三、使用C库函数strtok
  • 四、使用regex_token_iterator(正则表达式)
  • 总结

如:

string str1 = "This is a test";
string str2 = "This-is-a-test";
string str2 = "This+is+a+test";

我们如何将以上字符串按照某种分隔符( ,-,+),将其分割成四个子串,其值分别为 “This” “is” “a” “test” 。

一、使用stringstream流

这里我们只需要用到 istringstream(字符串输入流) 构造字符串流,然后从字符串流中按照一定的格式读取数据即可。

通常我们使用 cin 从流中读取数据,而我们也可以使用 getline 读取,而后者在读取时可以选择接受的数据格式,其函数原型如下:

// istream & getline(char* buf, int bufSize);    // 读到 \n 为止
istream & getline(char* buf, int bufSize, char delim); //读到 delim 字符为止
                // \n 或 delim 都不会被读入 buf,但会被从文件输入流缓冲区中取走

因此,我们可以按照此方式设计一个C++中的string split函数。

void Stringsplit(string str,const const char split)
{
    istringstream iss(str);    // 输入流
    string token;            // 接收缓冲区
    while (getline(iss, token, split))    // 以split为分隔符
    {
        cout << token << endl; // 输出
    }
}

如此,我们就设计出了我们的Stringsplit() 函数。该函数有以下 2 种语法格式

void Stringsplit(string str,const const char split);
// 默认将传入的字符串str以split为分隔符进行分割,并将得到的子串打印在屏幕上,无返回值
void Stringsplit(string str, const const char split,vector<string>& rst);
// 默认将传入的字符串str以split为分隔符进行分割,    不会将子串打印在屏幕上,无返回值
//                     分割的子串将会保存在rst数组中被带出函数。

以上,我们简单的设计了一种C++中的分割字符串的函数,下面来看一个测试用例:

int main() {
    string str("This is a test");
    Stringsplit(str, ' ');        // 打印子串

    vector<string> strList;
    string str2("This-is-a-test");
    Stringsplit(str2, '-', strList);    // 将子串存放到strList中
    for (auto s : strList)
        cout << s << " ";
    cout << endl;
    return 0;
}

# 输出
This
is
a
test
This is a test

二、使用string类提供的find方法与substr方法

find函数原型:

size_type find( const basic_string& str, size_type pos = 0 ) const;

参数:

str - 要搜索的 string , pos - 开始搜索的位置

返回值

找到的子串的首字符位置,或若找不到这种子串则为 npos 。

substr函数原型: 

basic_string substr( size_type pos = 0, size_type count = npos ) const;

参数:

pos - 要包含的首个字符的位置 ,count - 子串的长度

返回值

含子串 [pos, pos+count) 的 string 。

由以上两个函数我们便可以设计出我们的Stringsplit()来。同时,因为find()函数查找的可以是字符串,因此我们的分隔符可以是单个的字符,也可以是一个字符串。

// 使用字符分割
void Stringsplit(const string& str, const char split, vector<string>& res)
{
    if (str == "")        return;
    //在字符串末尾也加入分隔符,方便截取最后一段
    string strs = str + split;
    size_t pos = strs.find(split);

    // 若找不到内容则字符串搜索函数返回 npos
    while (pos != strs.npos)
    {
        string temp = strs.substr(0, pos);
        res.push_back(temp);
        //去掉已分割的字符串,在剩下的字符串中进行分割
        strs = strs.substr(pos + 1, strs.size());
        pos = strs.find(split);
    }
}
// 使用字符串分割
void Stringsplit(const string& str, const string& splits, vector<string>& res)
{
    if (str == "")        return;
    //在字符串末尾也加入分隔符,方便截取最后一段
    string strs = str + splits;
    size_t pos = strs.find(splits);
    int step = splits.size();

    // 若找不到内容则字符串搜索函数返回 npos
    while (pos != strs.npos)
    {
        string temp = strs.substr(0, pos);
        res.push_back(temp);
        //去掉已分割的字符串,在剩下的字符串中进行分割
        strs = strs.substr(pos + step, strs.size());
        pos = strs.find(splits);
    }
}

下面是一个测试用例:

int main()
{
    vector<string> strList;
    string str("This-is-a-test");
    Stringsplit(str, '-', strList);
    for (auto s : strList)
        cout << s << " ";
    cout << endl;

    vector<string> strList2;
    string str2("This%20is%20a%20test");
    Stringsplit(str2, "%20", strList2);
    for (auto s : strList2)
        cout << s << " ";
    cout << endl;
    return 0;
}

# 输出
This is a test
This is a test

三、使用C库函数strtok

char* strtok( char* str, const char* delim );

参数:

  • str - 指向要记号化的空终止字节字符串的指针
  • delim - 指向标识分隔符的空终止字节字符串的指针

返回值:

指向下个记号起始的指针,或若无更多记号则为空指针。

需要注意的是,该函数使用一个全局的静态变量来保存每次分割后的位置,因此在多线程中是不安全的,这里我们也可以选择使用它的线程安全版本

 char *strtok_r(char *str, const char *delim, char **saveptr); 。
void Stringsplit(const string& str, const string& split, vector<string>& res)
{
    char* strc = new char[str.size() + 1];
    strcpy(strc, str.c_str());   // 将str拷贝到 char类型的strc中
    char* temp = strtok(strc, split.c_str());
    while (temp != NULL)
    {
        res.push_back(string(temp));
        temp = strtok(NULL, split.c_str());    // 下一个被分割的串
    }
    delete[] strc;
}

如此,我们的使用 strtok 版本的Stringsplit() 就完成了。不过,我们使用这种方法实现的字符串分割函数只能根据字符来分割,而我们传入的参数是字符串类型,这样可能会对函数的使用这造成误导(注:参数传入字符串用的双引号,传入字符用的单引号),因此我们也可以使用下面的方法封装一个参数是字符类型的函数。

void Stringsplit(const string& str, const char split, vector<string>& res)
{
    Stringsplit(str, string(1,split), res);    // 调用上一个版本的Stringsplit()
}

下面给出一个测试用例,我们分别使用单/双引号传入分割的限定字符。

int main()
{
    vector<string> strList;
    string str("This+is+a+test");
    Stringsplit(str, '+', strList);
    for (auto s : strList)
        cout << s << " ";
    cout << endl;

    vector<string> strList2;
    string str2("This-is-a-test");
    Stringsplit(str2, "-", strList2);
    for (auto s : strList2)
        cout << s << " ";
    cout << endl;
    return 0;
}

四、使用regex_token_iterator(正则表达式)

正则表达式(regular expression)描述了一种字符串匹配的模式(pattern),可以用来检查一个串是否含有某种子串、将匹配的子串替换或者从某个串中取出符合某个条件的子串等。

而在C++的正则中,把这种操作称为Tokenize分词(或者叫切割)。这种操作刚好可以满足我们的需求,用模板类regex_token_iterator<>提供分词迭代器,可以完成字符串的分割。

void Stringsplit(const string& str, const string& split, vector<string>& res)
{
    //std::regex ws_re("\\s+"); // 正则表达式,匹配空格
    std::regex reg(split);        // 匹配split
    std::sregex_token_iterator pos(str.begin(), str.end(), reg, -1);
    decltype(pos) end;              // 自动推导类型
    for (; pos != end; ++pos)
    {
        res.push_back(pos->str());
    }
}

测试用例:

int main()
{
    // 单个字符分词
    vector<string> strList;
    string str("This is a test");
    Stringsplit(str," ", strList);
    for (auto s : strList)
        cout << s << " ";
    cout << endl;

    // 使用字符串分词
    vector<string> strList2;
    string str2("ThisABCisABCaABCtest");
    Stringsplit(str2, "ABC", strList2);
    for (auto s : strList2)
        cout << s << " ";
    cout << endl;
}

# 输出
This is a test
This is a test

总结

到此这篇关于C++中string字符串分割函数split()的4种实现方法的文章就介绍到这了,更多相关C++ 字符串分割函数split()内容请搜索我们以前的文章或继续浏览下面的相关文章希望大家以后多多支持我们!

(0)

相关推荐

  • 如何在c++中实现字符串分割函数split详解

    前言 在学习c++中string相关基本用法的时候,发现了sstream的istringstream[1]可以将字符串类似于控制台的方式进行输入,而实质上这个行为等同于利用空格将一个字符串进行了分割,于是考虑到可以利用这个特性来实现c++库函数中没有的字符串分割函数split string src("Avatar 123 5.2 Titanic K"); istringstream istrStream(src); //建立src到istrStream的联系 string s1, s2

  • C++中string字符串分割函数split()的4种实现方法

    目录 一.使用stringstream流 二.使用string类提供的find方法与substr方法 三.使用C库函数strtok 四.使用regex_token_iterator(正则表达式) 总结 如: string str1 = "This is a test"; string str2 = "This-is-a-test"; string str2 = "This+is+a+test"; 我们如何将以上字符串按照某种分隔符( ,-,+),

  • JavaScript中字符串分割函数split用法实例

    本文实例讲述了JavaScript中字符串分割函数split用法.分享给大家供大家参考.具体如下: 先来看下面这段代码: <script type="text/javascript"> var str="How are you doing today?" document.write(str.split(" ") + "<br />") document.write(str.split("&q

  • c语言中字符串分割函数及实现方法

    1.问题引入 自己在写一个linux下的模拟执行指令的时候,遇到了输入"cat a.c",要将该字符串分解成cat和a.c两个单独的字符串,虽然知道有strtok的存在,但是想自己尝试写一下,于是就自己写了一个,不过总是遇到这样或那样的问题,虽然最后调通了,不过确浪费了不少时间:后来作业交上去以后又仔细阅读了strtok函数,发现原来linux下已经改成strsep,所有在这里就写一下自己所走的过程. 2.自己写的字符串分割函数:用于分割指令,比如cat a.c最后会被分割成cat和a

  • python语言中pandas字符串分割str.split()函数

    目录 前言 1.常规赛数据格式 2.计算詹姆斯常规赛命中率 总结 前言 为了介绍python语言中pandas库在数据分析中的重要作用,本人打算以NBA球星勒布朗詹姆斯在2020-2021赛季常规赛个人数据为例对pandas相关函数进行详细说明.利用爬虫技术,在知名篮球网站虎扑爬取了勒布朗詹姆斯的数据,稍后会将数据上传至csdn,以供大家下载. 这篇文章,详细介绍了pandas字符串分割函数---str.split()的用法. DataFrame.str.split(pa,n,expand)pa

  • php字符串分割函数用法实例

    本文实例讲述了php字符串分割函数用法.分享给大家供大家参考.具体分析如下: php中explode 和 split 函数用来分割字符串. explode函数语法如下 explode(substring, string) explode函数通过子字符串进行分割,效率比split要高 split函数语法如下 split(pattern, string) split通过正则表达式对字符串进行分割,效率相对explode要低,但是功能强大 <?php $list = explode("_&quo

  • C++的字符串分割函数的使用详解

    经常碰到字符串分割的问题,这里总结下,也方便我以后使用. 一.用strtok函数进行字符串分割 原型: char *strtok(char *str, const char *delim); 功能:分解字符串为一组字符串. 参数说明:str为要分解的字符串,delim为分隔符字符串. 返回值:从str开头开始的一个个被分割的串.当没有被分割的串时则返回NULL. 其它:strtok函数线程不安全,可以使用strtok_r替代. 示例: //借助strtok实现split #include <st

  • 带你用C语言实现strtok和字符串分割函数

    目录 前言 一.strtok的基本使用 二.strtok的实现 总结 前言 字符串分割函数strtok,大家可能都知道他怎么使用,一旦要用的时候就会心生疑惑,不知道它的内部的实现,废话不多说,本篇就来带大家看看strtok的基本使用和实现 一.strtok的基本使用 解析:函数大概说了以下几点 1.str就是我们要去拆分的字符串,注意,我们会对该字符串进行更改,所以一般我们会拷贝一份然后去分割拷贝的那份字符串!! 2.delimiters 就是我们定义的切分的符号,假如想要用空格作为分割符,我们

  • PostgreSQL常用字符串分割函数整理汇总

    目录 1. SPLIT_PART 2.STRING_TO_ARRAY 3. regexp_split_to_array 4.regexp_split_to_array 5. regexp_matches 总结 1. SPLIT_PART SPLIT_PART() 函数通过指定分隔符分割字符串,并返回第N个子串.语法: SPLIT_PART(string, delimiter, position) string : 待分割的字符串 delimiter:指定分割字符串 position:返回第几个字

  • python中根据字符串调用函数的实现方法

    在python中可以根据字符串来调用函数: 1.使用getattr从字符串来调用函数 在多进程中,可能传递过来的是一个字符串,那么我怎么来调用一个已经存在的函数呢,主要就是使用到getattr函数的作用,这个函数就是在使用字符串得到这个字符串对应的函数的对象,然后就可以进行执行,如下所示: 在模块中,存在两个函数: [root@python 530]# cat attr.py #!/usr/bin/env python def kel(): print 'this is a kel functi

随机推荐