C++程序 将字符串拆分为多个子字符串
按某个分隔符拆分字符串是一个非常常见的任务。例如,我们有一个从文件中得到的逗号分隔的项目列表,我们想要在数组中拥有各个项目。
几乎所有的编程语言都提供了一种函数,以某个分隔符拆分字符串。
在C++中
注意:strtok()的主要缺点是它仅适用于C风格的字符串。
因此,我们需要显式地将C++字符串转换为char数组。
许多程序员不知道C++有两个额外的API,这些API更优雅并处理C++字符串。
方法1:使用C++的stringstream API
先决条件 :stringstream API
可以使用字符串对象初始化stringstream对象,它会自动将字符串标记为一个空格字符。 就像“cin”流一样,stringstream允许您将字符串读取为一系列单词流。
一些最常用的StringStream函数。
clear() – 刷新流
str() — 将一系列单词转换为C++字符串对象。
operator << — 将一个字符串对象推入流中。
operator >> — 从流中获取一个单词。
下面的代码演示了它。
#include <bits/stdc++.h>
using namespace std;
// A quick way to split strings separated via spaces.
void simple_tokenizer(string s)
{
stringstream ss(s);
string word;
while (ss >> word) {
cout << word << endl;
}
}
int main(int argc, char const* argv[])
{
string a = "How do you do!";
// Takes only space separated C++ strings.
simple_tokenizer(a);
cout << endl;
return 0;
}
输出:
How
do
you
do!
方法2:使用C++ find()和substr() API。
先决条件: find函数 和 substr() 。
这种方法更加健壮,可以解析带有任何分隔符的字符串,而不仅仅是空格(虽然默认行为是在空格上分离)。 从下面的代码中可以很容易地理解逻辑。
#include <bits/stdc++.h>
using namespace std;
void tokenize(string s, string del = " ")
{
int start = 0;
int end = s.find(del);
while (end != -1) {
cout << s.substr(start, end - start) << endl;
start = end + del.size();
end = s.find(del, start);
}
cout << s.substr(start, end - start);
}
int main(int argc, char const* argv[])
{
// Takes C++ string with any separator
string a = "Hi%do%you%do%!";
tokenize(a, "$%");
cout << endl;
return 0;
}
输出:
Hi
do
you
do
!
方法3:使用临时字符串
如果您知道分隔符的长度为1,则可以简单地使用一个临时字符串来拆分字符串。这种方法可以节省在方法2的情况下函数的开销时间。
#include <iostream>
using namespace std;
void split(string str, char del){
// 声明一个临时字符串,用于存储当前到分隔符为止的“单词”
string temp = "";
for(int i=0; i<(int)str.size(); i++){
// 如果当前字符不是分隔符,则将其附加到当前“单词”中,否则
// 说明已经完成了这个“单词”,将其打印出来,并开始一个新的“单词”。
if(str[i] != del){
temp += str[i];
}
else{
cout << temp << " ";
temp = "";
}
}
cout << temp;
}
int main() {
string str = "geeks_for_geeks"; // 要拆分的字符串
char del = '_'; // 字符串的分隔符
split(str, del);
return 0;
}
输出
geeks for geeks
时间复杂度: O(n) 其中 n 是字符串的长度。
辅助空间: O(1)