主要来源leetcode
https://leetcode-cn.com/explore/learn/card/array-and-string/200/introduction-to-string/
字符串特性
字符串实际上是一个 unicode 字符数组。你可以执行几乎所有我们在数组中使用的操作。
比较函数 C++支持运算符重载,我们可以使用 “==” 来比较两个字符串。
java不支持。
compare 函数:等于返回0,大于时返回1,小于时返回-1;
#include <iostream>
using namespace std;
int main() {
string s1 = "Hello World";
cout << "s1 is \"Hello World\"" << endl;
string s2 = s1;
cout << "s2 is initialized by s1" << endl;
string s3(s1);
cout << "s3 is initialized by s1" << endl;
// compare by '=='
cout << "Compared by '==':" << endl;
cout << "s1 and \"Hello World\": " << (s1 == "Hello World") << endl;
cout << "s1 and s2: " << (s1 == s2) << endl;
cout << "s1 and s3: " << (s1 == s3) << endl;
// compare by 'compare'
s2="Aello World";
s3="Zello World";
cout << "Compared by 'compare':" << endl;
cout << "s1 and \"Hello World\": " << s1.compare("Hello World") << endl;
cout << "s1 and s2: " << s1.compare(s2) << endl;
cout << "s1 and s3: " << s1.compare(s3) << endl;
}
s1 is "Hello World"
s2 is initialized by s1
s3 is initialized by s1
Compared by '==':
s1 and "Hello World": 1
s1 and s2: 1
s1 and s3: 1
Compared by 'compare':
s1 and "Hello World": 0
s1 and s2: 1
s1 and s3: -1
是否可变
不可变意味着一旦字符串被初始化,你就无法改变它的内容。
在某些语言(如 C ++)中,字符串是可变的。 也就是说,你可以像在数组中那样修改字符串。
在其他一些语言(如 Java)中,字符串是不可变的。 此特性将带来一些问题。 我们将在下一篇文章中阐明问题和解决方案。
#include <iostream>
int main() {
string s1 = "Hello World";
s1[5] = ',';
cout << s1 << endl;
}
额外操作
数组相比,我们可以对字符串执行一些额外的操作。这里有一些例子:
find()和rfind()分别表示从前和从后开始检索。返回位置下标(下标从0开始);
substr()函数,返回子串,arg1 为子串开始位置,arg2 为子串长度。
#include <iostream>
int main() {
string s1 = "Hello World";
// 1. concatenate
s1 += "!";
cout << s1 << endl;
// 2. find
cout << "The position of first 'o' is: " << s1.find('o') << endl;
cout << "The position of last 'o' is: " << s1.rfind('o') << endl;
// 3. get substr
cout << s1.substr(6, 5) << endl;
}
Hello World!
The position of first 'o' is: 4
The position of last 'o' is: 7
World
如果字符串的长度是 N,那么查找操作和子字符串操作的时间复杂度是 O(N)。
字符串分割
将str ,按pattern 分割
实现方法:
因为string尾部可能不存在pattern,即pattern 数可能大于段数。因此,首先在str尾部append 一个pattern,则减少了if语句的判断,简化代码。
size_t 和 int 区别:
为什么有时候不用int,而是用size_type或者size_t:
与int固定四个字节不同有所不同,size_t的取值range是目标平台下最大可能的数组尺寸,一些平台下size_t的范围小于int的正数范围,又或者大于unsigned
int. 使用Int既有可能浪费,又有可能范围不够大。
————————————————
原文链接:https://blog.csdn.net/qq_41598072/article/details/84924997
vector<string> split(const string& str, const string& pattern)
{
vector<string> res;
if (str == "")
return res;
string strs = str + pattern;
size_t pos = strs.find(pattern);
while (pos != strs.npos)
{
string temp = strs.substr(0, pos);
res.push_back(temp);
strs = strs.substr(pos + 1, strs.size());
pos = strs.find(pattern);
}
return res;
}
倒转
1.对于用char定义的字符串:使用string.h中的strrev函数
#include <iostream>
#include <cstring>
using namespace std;
int main()
{
char s[]="123456";//不能是string类型;
strrev(s);
cout<<s<<endl;
return 0;
}
2.对于string类型的:使用algorithm中的reverse函数
复制代码
#include<iostream>
#include <cstring>
#include <algorithm>
using namespace std;
int main()
{
string s[]="123456";
reverse(s.begin(),s.end());
cout<<s<<endl;
return 0;
}
例题
二进制求和
Given two binary strings, return their sum (also a binary string).
The input strings are both non-empty and contains only characters 1 or 0.
Example 1:
Input: a = “11”, b = “1”
Output: “100”
Example 2:
Input: a = “1010”, b = “1011”
Output: “10101”
注意点:
不能直接转成int然后使用位操作,因为并未提及string的长度,可能超过。
在判断长度的基础上,可申请多个int变量,每个int变量可容纳32位bits.
在32的机器下,int的范围是 - 2 ^ 31 ~2 ^ 31 - 1; 也就是:[-2147483648, 2147483647]
解法一:
string 实现方案:直接按常理实现,先将长度统一,并添加进位flag;
class Solution {
public:
string addBinary(string a, string b) {
bool step_flag = false;
if(a.size()>b.size())
b.insert(b.begin(), a.size()-b.size(), '0');
else if (b.size()>a.size()) {
a.insert(a.begin(), b.size()-a.size(), '0');
}
string res;
for (int i = a.size()-1; i>=0; i--)
if (!step_flag)
{
if (a[i] == '1' && b[i] == '1')
{
res += '0';
step_flag = true;
}
else if (a[i] == '0' && b[i] == '0')
res += '0';
else
res += '1';
}
else
{
step_flag = false;
if (a[i] == '1' && b[i] == '1')
{
res += '1';
step_flag = true;
}
else if (a[i] == '0' && b[i] == '0')
res+= '1';
else
{
res += '0';
step_flag = true;
}
}
if (step_flag)
res += '1';
reverse(res.begin(), res.end());
return res;
}
};
思路二:
string 实现方案:
核心思想:虽然不能完全转化为位运算,但可以局部转化为bit运算。
利用一个int 类型num 来储存两位的计算结果(a[–al]-'0’将string 转为int),将(num&1)个位存入结果序列后,利用位操作的右移计算(num>>=1),将进位情况保留到下一轮计算。
class Solution {
public:
string addBinary(string a, string b) {
string s(max(a.size(),b.size())+1,'0');
int al=a.size();
int bl=b.size();
int num=0;
for(int i=s.size();al||bl||num;num>>=1)
{
if(al)
num+=a[--al]-'0';
if(bl)
num+=b[--bl]-'0';
s[--i]=(num&1)+'0';
}
if(s[0]=='0')
s.erase(0,1);
return s;
}
};
Implement strStr()
Implement strStr().
Return the index of the first occurrence of needle in haystack, or -1 if needle is not part of haystack.
Example 1:
Input: haystack = “hello”, needle = “ll”
Output: 2
Example 2:
Input: haystack = “aaaaa”, needle = “bba”
Output: -1
Clarification:
What should we return when needle is an empty string? This is a great question to ask during an interview.
For the purpose of this problem, we will return 0 when needle is an empty string. This is consistent to C’s strstr() and Java’s indexOf().
思路一,调用find函数
class Solution {
public:
int strStr(string haystack, string needle) {
if (!needle.empty())
return haystack.find(needle);
else
return 0;
}
};
思路二,朴素匹配算法。
class Solution {
public:
int strStr(string haystack, string needle) {
int res=-1;
if(needle.empty())
return 0;
if (needle.size()<=haystack.size())
{
int n = needle.size();
for (int i = 0; i < haystack.size() - n + 1; i++)
{
if (needle == haystack.substr(i, n))
{
res = i;
break;
}
}
}
return res;
}
};
最长公共前缀
Write a function to find the longest common prefix string amongst an array of strings.
If there is no common prefix, return an empty string “”.
Example 1:
Input: [“flower”,“flow”,“flight”]
Output: “fl”
Example 2:
Input: [“dog”,“racecar”,“car”]
Output: “”
Explanation: There is no common prefix among the input strings.
Note:
All given inputs are in lowercase letters a-z.
注意点:string 为空 和string数据为1的情况。
思路一:朴素思想,暴力循环,一位位比较。
class Solution {
public:
string longestCommonPrefix(vector<string>& strs) {
int length=0;
bool flag = false;
if (strs.size() < 1)
return "";
else if (strs.size() == 1)
return strs[0];
else if(strs.size()>1)
for (int i = 0; i < strs[0].size(); i++)
{
char Common=strs[0][i];
for (int j = 1; j < strs.size(); j++)
if (strs[j][i] != Common)
{
flag = true; break;
}
if (flag)
break;
length++;
}
cout << length<<endl;
return strs[0].substr(0, length);
}
};