1.替换空格
请实现一个函数,将一个字符串中的空格替换成“%20”。例如,当字符串为We Are Happy.则经过替换之后的字符串为We%20Are%20Happy。
class Solution {
public:
void replaceSpace(char str[],int length) {
if(str==NULL||length<=0){
return;
}
int originallength=0;
int numberofblank=0;
int i=0;
while(str[i]!='\0'){
++originallength;
if(str[i]==' ')
++numberofblank;
++i;
}
int newlength=originallength+numberofblank*2;
if(newlength>length)
return;
int indexoforiginal=originallength;
int indexofnew=newlength;
while(indexoforiginal>=0&&indexofnew>indexoforiginal){
if(str[indexoforiginal]==' '){
str[indexofnew--]='0';
str[indexofnew--]='2';
str[indexofnew--]='%';
}else{
str[indexofnew--]=str[indexoforiginal];
}
--indexoforiginal;
}
}
};
2.确定字符互异
请实现一个算法,确定一个字符串的所有字符是否全都不同。这里我们要求不允许使用额外的存储结构。
给定一个string iniString,请返回一个bool值,True代表所有字符全都不同,False代表存在相同的字符。保证字符串中的字符为ASCII字符。字符串的长度小于等于3000。
测试样例:
"aeiou"
返回:True
"BarackObama"
返回:False
class Different {
public:
bool checkDifferent(string iniString) {
// write code here
for(int i=0;i<iniString.length()-1;i++){
for(int j=i+1;j<iniString.length();j++){
if(iniString[i]==iniString[j])
return false;
}
}
return true;
}
};
3.字符串的排列
输入一个字符串,按字典序打印出该字符串中字符的所有排列。例如输入字符串abc,则打印出由字符a,b,c所能排列出来的所有字符串abc,acb,bac,bca,cab和cba。 结果请按字母顺序输出。
输入描述:
输入一个字符串,长度不超过9(可能有字符重复),字符只包括大小写字母。
class Solution {
public:
vector<string> Permutation(string str) {
//可以用递归来做
vector<string> array;
if(str.size()==0)
return array;
Permutation(array, str, 0);
sort(array.begin(), array.end());
return array;
}
void Permutation(vector<string> &array, string str, int begin)//遍历第begin位的所有可能性
{
if(begin==str.size()-1)
array.push_back(str);
for(int i=begin; i<=str.size()-1;i++)
{
if(i!=begin && str[i]==str[begin])//有重复字符时,跳过
continue;
swap(str[i], str[begin]);//当i==begin时,也要遍历其后面的所有字符;
//当i!=begin时,先交换,使第begin位取到不同的可能字符,再遍历后面的字符
Permutation(array, str, begin+1);//遍历其后面的所有字符;
swap(str[i], str[begin]);//为了防止重复的情况,还需要将begin处的元素重新换回来
/*举例来说“abca”,为什么使用了两次swap函数
交换时是a与b交换,遍历;
交换时是a与c交换,遍历;(使用一次swap时,是b与c交换)
交换时是a与a不交换;
*/
}
}
};
4.第一个只出现一次的字符
在一个字符串(1<=字符串长度<=10000,全部由大写字母组成)中找到第一个只出现一次的字符,并返回它的位置
class Solution {
public:
int FirstNotRepeatingChar(string str) {
if(str.length()==0)
return -1;
int hash[256]={0};
int i=0;
while(str[i]!='\0'){
hash[str[i]]++;
++i;
}
i=0;
while(str[i]!='\0'){
if(1==hash[str[i]]){
return i;
}
i++;
}
return -1;
}
};
5.左旋转字符串
汇编语言中有一种移位指令叫做循环左移(ROL),现在有个简单的任务,就是用字符串模拟这个指令的运算结果。对于一个给定的字符序列S,请你把其循环左移K位后的序列输出。例如,字符序列S=”abcXYZdef”,要求输出循环左移3位后的结果,即“XYZdefabc”。是不是很简单?OK,搞定它!
class Solution {
public:
void fun(string &s,int start,int end)
{
char temp;
while(start<end)
{
temp=s[start];
s[start]=s[end];
s[end]=temp;
start++;
end--;
}
}
string LeftRotateString(string str, int n) {
int len=str.length();
if(0==len || 0==n)
return str;
string &temp=str;
fun(temp,0,n-1);
fun(temp,n,len-1);
fun(temp,0,len-1);
return str;
}
};
6.正则表达式匹配
请实现一个函数用来匹配包括'.'和'*'的正则表达式。模式中的字符'.'表示任意一个字符,而'*'表示它前面的字符可以出现任意次(包含0次)。 在本题中,匹配是指字符串的所有字符匹配整个模式。例如,字符串"aaa"与模式"a.a"和"ab*ac*a"匹配,但是与"aa.a"和"ab*a"均不匹配
/*
思路:只有当模式串和字符串同时等于\0,才可以认为两个串匹配。
在匹配中,对于每个位的匹配可以分为三种情况
1、(相应位匹配||模式串为.&&字符串不是\0)&&模式串下一位是*
2、(相应位匹配||模式串为.&&字符串不是\0)&&模式串下一位不是*
3、相应位不匹配&&(模式位不为.||字符串是\0)
对应1,最复杂。分为*取0,*取1,*>=2三种情况。
*取0对应跳过当前匹配位,继续寻找patter的下一个匹配位,str不变,pattern+2
*取1对应当前匹配位算一次成功匹配,str+1,pattern+2
*取>=2对应一次成功匹配,继续匹配字符串的下一位是否匹配,str+1,pattern不变
三者取或。即只要有一种情况能匹配成功认为字符串就是匹配成功的。
对应2,相当于一次成功匹配,str+1,pattern+1
对应3,匹配失败,直接返回false
*/
class Solution {
public:
bool match(char* str, char* pattern)
{
if(str==NULL||pattern==NULL)
return false;
return matchCore(str,pattern);
}
bool matchCore(char* str, char* pattern)
{
if(*str=='\0'&&*pattern=='\0')
return true;
if(*str!='\0'&&*pattern=='\0')
return false;
if(*(pattern+1)=='*')
{
if(*pattern==*str||(*pattern=='.'&&*str!='\0'))
return matchCore(str+1,pattern+2)||matchCore(str+1,pattern)||matchCore(str,pattern+2);
else
return matchCore(str,pattern+2);
}
if(*str==*pattern||(*pattern=='.'&&*str!='\0'))
return matchCore(str+1,pattern+1);
return false;
}
};
7.把字符串转换成整数
将一个字符串转换成一个整数,要求不能使用字符串转换整数的库函数。
class Solution {
public:
/*
1、首先有可能有正负号,也有可能没有
2、当输入字符串中有非数字的时候输出为0;
*/
int StrToInt(string str)
{
bool g_InvalidValue = false;
if(str.size()<=0)
{
g_InvalidValue = true;
return 0;
}
int i = 0;
int sum = 0;
bool isPositive = false;
if(str[i]=='-')
{
isPositive = true;
i++;
}
else if(str[i]=='+')
{
i++;
}
while(str[i])
{
if(str[i]<='9'&&str[i]>='0')
{
sum = sum*10+str[i]-'0'+0;
}
else
{
g_InvalidValue = true;
return 0;
}
i++;
}
if(isPositive)
sum = -sum;
return sum;
}
};
8.原串翻转
请实现一个算法,在不使用额外数据结构和储存空间的情况下,翻转一个给定的字符串(可以使用单个过程变量)。
给定一个string iniString,请返回一个string,为翻转后的字符串。保证字符串的长度小于等于5000。
测试样例:
"This is nowcoder"
返回:"redocwon si sihT"
class Reverse {
public:
string reverseString(string iniString)
{
// write code here
int length=iniString.size();
int middle=length>>1;//交换时间复杂度O(n);计算次数n/2
if(length<1)
return NULL;
int end=length-1;
for(int i=0;i<=middle,i<=end;i++,end--)
{
int temp=iniString[i];
iniString[i]=iniString[end];
iniString[end]=temp;
}
return iniString;
}
};
9.确定两串乱序同构
给定两个字符串,请编写程序,确定其中一个字符串的字符重新排列后,能否变成另一个字符串。这里规定大小写为不同字符,且考虑字符串重点空格。
给定一个string stringA和一个string stringB,请返回一个bool,代表两串是否重新排列后可相同。保证两串的长度都小于等于5000。
测试样例:
"This is nowcoder","is This nowcoder"
返回:true
"Here you are","Are you here"
返回:false
class Same {
public:
bool checkSam(string stringA, string stringB) {
// write code here
int sizeA=stringA.size();
int sizeB=stringB.size();
int A[256]={0};
int B[256]={0};
if(sizeA!=sizeB)
return false;
for(int i=0;i<sizeA;i++){
A[stringA[i]]++;
B[stringB[i]]++;
}
for(int j=0;j<256;j++){
if(A[j]!=B[j])
return false;
}
return true;
}
};
10.基本字符串压缩
利用字符重复出现的次数,编写一个方法,实现基本的字符串压缩功能。比如,字符串“aabcccccaaa”经压缩会变成“a2b1c5a3”。若压缩后的字符串没有变短,则返回原先的字符串。
给定一个string iniString为待压缩的串(长度小于等于3000),保证串内字符均由大小写英文字母组成,返回一个string,为所求的压缩后或未变化的串。
测试样例
"aabcccccaaa"
返回:"a2b1c5a3"
"welcometonowcoderrrrr"
返回:"welcometonowcoderrrrr"
class Zipper {
public:
string zipString(string iniString) {
// write code here
string s;
for(int i=0;i<iniString.length();i++){
int count=1;
while(i<iniString.length()&&iniString[i]==iniString[i+1])
{
count++;
i++;
}
s+=iniString[i];
s+=to_string(count);
}
if(iniString.length()>s.length()) return s;
return iniString;
}
};
11.翻转子串
题目描述
假定我们都知道非常高效的算法来检查一个单词是否为其他字符串的子串。请将这个算法编写成一个函数,给定两个字符串s1和s2,请编写代码检查s2是否为s1旋转而成,要求只能调用一次检查子串的函数。
给定两个字符串s1,s2,请返回bool值代表s2是否由s1旋转而成。字符串中字符为英文字母和空格,区分大小写,字符串长度小于等于1000。
测试样例:
"Hello world","worldhello "
返回:false
"waterbottle","erbottlewat"
返回:true
/*以s1=ABCD为例,我们先分析s1进行循环移位之后的结果:
ABCD->BCDA->CDAB->DABC->ABCD .......
假设我们把前面移走的数据进行保留:
ABCD->ABCDA->ABCDAB->ABCDABC->ABCDABCD.....
因此看出,对s1做循环移位,所得字符串都将是字符串s1s1的子字符串。如果s2可以由s1循环移位得到,则一定可以在s1s1上。*/
class ReverseEqual {
public:
bool checkReverseEqual(string s1, string s2) {
int size1 = s1.size();
int size2 = s2.size();
if(size1 == 0 || size2 == 0){
return false;
}//if
string str = s1 + s1;
if(str.find(s2) == -1){
return false;
}//if
return true;
}
};
12.单词最近距离
有一篇文章内含多个单词,现给定两个单词,请设计一个高效算法,找出文中这两个单词的最短距离(即最少相隔的单词数,也就是两个单词在文章中位置的差的绝对值)。
给定一个string数组article,代表所给文章,同时给定文章的单词数n和待查找的两个单词x和y。请返回两个单词的最短距离。保证两个单词均在文中出现且不相同,同时保证文章单词数小于等于1000。
class Distance {
public:
int getDistance(vector<string> article, int n, string x, string y) {
// write code here
int p=-1;
int distance = 1000;
int i;
for(i=0;i<article.size();i++){
if(article[i] == x || article[i] == y){
if(p != -1 && article[i] != article[p]){
distance = min(distance,abs(i-p));
}
p = i;
}
}
return distance;
}
};
13.字符串最后一个单词的长度
计算字符串最后一个单词的长度,单词以空格隔开。
输入描述:
一行字符串,非空,长度小于5000。
输出描述:
整数N,最后一个单词的长度。
输入例子:
hello world
输出例子:
5
#include<iostream>
#include<string>
using namespace std;
int main(){
string s;
while(getline(cin,s)){
int i=0;
int flag=1;
int n=0;
for(i=s.length()-1;i>=0;i--){
if(flag && s[i]==' ')
continue;
else if(s[i]!=' '){
flag=0;
++n;
}
else
break;
}
cout << n << endl;
}
}
14.计算字符个数
写出一个程序,接受一个有字母和数字以及空格组成的字符串,和一个字符,然后输出输入字符串中含有该字符的个数。不区分大小写。
输入描述:
输入一个有字母和数字以及空格组成的字符串,和一个字符。
输出描述:
输出输入字符串中含有该字符的个数。
输入例子:
ABCDEF
A
输出例子:
1
#include<iostream>
#include<string>
using namespace std;
int main(){
string s;
char t,t1;
getline(cin,s);
cin>>t;
if(t>=65&&t<=96)
t1=t+32;
if(t>=97&&t<=129)a
t1=t-32;
int i;
int count=0;
for(i=0;i<=s.length();i++){
if(s[i]==t||s[i]==t1)
count++;
}
cout<<count<<endl;
return 0;
}
15.字符个数统计
编写一个函数,计算字符串中含有的不同字符的个数。字符在ACSII码范围内(0~127)。不在范围内的不作统计。
输入描述:
输入N个字符,字符在ACSII码范围内(0~127)。
输出描述:
输出字符的个数。
输入例子:
abc
输出例子:
3
#include<iostream>
using namespace std;
int main(){
char ch;
int arr[128]={0};
int count=0;
while(cin>>ch){
if(ch>=0 && ch<=127){
arr[ch]++;
}
}
for(int i=0;i<128;i++){
if(arr[i]>0)
count++;
}
cout<<count<<endl;
return 0;
}
16.字符串分隔
连续输入字符串,请按长度为8拆分每个字符串后输出到新的字符串数组;
•长度不是8整数倍的字符串请在后面补数字0,空字符串不处理。
输入描述:
连续输入字符串(输入2次,每个字符串长度小于100)
输出描述:
输出到长度为8的新字符串数组
输入例子:
abc
123456789
输出例子:
abc00000
12345678
90000000
#include <stdio.h>
#include <iostream>
#include <string>
using namespace std;
/* 测试数据不止有一组 */
int main()
{
string s1;
string s2 = "0000000";
unsigned int i = 0;
while ( getline(cin, s1) )
{
for (i = 0; i+8 < s1.length(); i=i+8)
{
cout << s1.substr(i, 8) << endl;
}
if (s1.length() - i > 0)
{
cout << s1.substr(i, s1.length() - i) + s2.substr(0, 8-(s1.length() - i))<< endl;
}
}
return 0;
}
17.字符串反转
写出一个程序,接受一个字符串,然后输出该字符串反转后的字符串。例如:
输入描述:
输入N个字符
输出描述:
输出该字符串反转后的字符串
输入例子:
abcd
输出例子:
dcba
#include<iostream>
#include<string>
using namespace std;
int main()
{
string s;
while(getline(cin,s))
{
int length;
length=s.length();
int i;
for(i=0;i<length;i++)
{
cout<<s[length-1-i];
}
cout<<endl;
}
}
18.句子逆序
将一个英文语句以单词为单位逆序排放。例如“I am a boy”,逆序排放后为“boy a am I”
所有单词之间用一个空格隔开,语句中除了英文字母外,不再包含其他字符
接口说明
/**
* 反转句子
*
* @param sentence 原句子
* @return 反转后的句子
*/
public String reverse(String sentence);
输入描述:
将一个英文语句以单词为单位逆序排放。
输出描述:
得到逆序的句子
输入例子:
I am a boy
输出例子:
boy a am I
#include <stdlib.h>
#include <stdio.h>
#include <string.h>
void ReverseWord(char *h,char *r)
{
while(h<r)
{
char tmp=*r;
*r--=*h;
*h++=tmp;
}
}
char *ReverseSentence(char *s)
{
char *p=s;
char *q=s;
//while(q)//Error
while(*q!='\0')
{
if(*q==' ')
{
ReverseWord(p,q-1);
q++;
p=q;
}else
q++;
}
ReverseWord(p,q-1);
ReverseWord(s,q-1);
return s;
}
int main()
{
char s[1000];//gets(s1);gets(s2);
while(gets(s)){
// printf("%s\n",s);
ReverseSentence(s);
printf("%s\n",s);
}
return 0;
}
请实现一个函数,将一个字符串中的空格替换成“%20”。例如,当字符串为We Are Happy.则经过替换之后的字符串为We%20Are%20Happy。
class Solution {
public:
void replaceSpace(char str[],int length) {
if(str==NULL||length<=0){
return;
}
int originallength=0;
int numberofblank=0;
int i=0;
while(str[i]!='\0'){
++originallength;
if(str[i]==' ')
++numberofblank;
++i;
}
int newlength=originallength+numberofblank*2;
if(newlength>length)
return;
int indexoforiginal=originallength;
int indexofnew=newlength;
while(indexoforiginal>=0&&indexofnew>indexoforiginal){
if(str[indexoforiginal]==' '){
str[indexofnew--]='0';
str[indexofnew--]='2';
str[indexofnew--]='%';
}else{
str[indexofnew--]=str[indexoforiginal];
}
--indexoforiginal;
}
}
};
2.确定字符互异
请实现一个算法,确定一个字符串的所有字符是否全都不同。这里我们要求不允许使用额外的存储结构。
给定一个string iniString,请返回一个bool值,True代表所有字符全都不同,False代表存在相同的字符。保证字符串中的字符为ASCII字符。字符串的长度小于等于3000。
测试样例:
"aeiou"
返回:True
"BarackObama"
返回:False
class Different {
public:
bool checkDifferent(string iniString) {
// write code here
for(int i=0;i<iniString.length()-1;i++){
for(int j=i+1;j<iniString.length();j++){
if(iniString[i]==iniString[j])
return false;
}
}
return true;
}
};
3.字符串的排列
输入一个字符串,按字典序打印出该字符串中字符的所有排列。例如输入字符串abc,则打印出由字符a,b,c所能排列出来的所有字符串abc,acb,bac,bca,cab和cba。 结果请按字母顺序输出。
输入描述:
输入一个字符串,长度不超过9(可能有字符重复),字符只包括大小写字母。
class Solution {
public:
vector<string> Permutation(string str) {
//可以用递归来做
vector<string> array;
if(str.size()==0)
return array;
Permutation(array, str, 0);
sort(array.begin(), array.end());
return array;
}
void Permutation(vector<string> &array, string str, int begin)//遍历第begin位的所有可能性
{
if(begin==str.size()-1)
array.push_back(str);
for(int i=begin; i<=str.size()-1;i++)
{
if(i!=begin && str[i]==str[begin])//有重复字符时,跳过
continue;
swap(str[i], str[begin]);//当i==begin时,也要遍历其后面的所有字符;
//当i!=begin时,先交换,使第begin位取到不同的可能字符,再遍历后面的字符
Permutation(array, str, begin+1);//遍历其后面的所有字符;
swap(str[i], str[begin]);//为了防止重复的情况,还需要将begin处的元素重新换回来
/*举例来说“abca”,为什么使用了两次swap函数
交换时是a与b交换,遍历;
交换时是a与c交换,遍历;(使用一次swap时,是b与c交换)
交换时是a与a不交换;
*/
}
}
};
4.第一个只出现一次的字符
在一个字符串(1<=字符串长度<=10000,全部由大写字母组成)中找到第一个只出现一次的字符,并返回它的位置
class Solution {
public:
int FirstNotRepeatingChar(string str) {
if(str.length()==0)
return -1;
int hash[256]={0};
int i=0;
while(str[i]!='\0'){
hash[str[i]]++;
++i;
}
i=0;
while(str[i]!='\0'){
if(1==hash[str[i]]){
return i;
}
i++;
}
return -1;
}
};
5.左旋转字符串
汇编语言中有一种移位指令叫做循环左移(ROL),现在有个简单的任务,就是用字符串模拟这个指令的运算结果。对于一个给定的字符序列S,请你把其循环左移K位后的序列输出。例如,字符序列S=”abcXYZdef”,要求输出循环左移3位后的结果,即“XYZdefabc”。是不是很简单?OK,搞定它!
class Solution {
public:
void fun(string &s,int start,int end)
{
char temp;
while(start<end)
{
temp=s[start];
s[start]=s[end];
s[end]=temp;
start++;
end--;
}
}
string LeftRotateString(string str, int n) {
int len=str.length();
if(0==len || 0==n)
return str;
string &temp=str;
fun(temp,0,n-1);
fun(temp,n,len-1);
fun(temp,0,len-1);
return str;
}
};
6.正则表达式匹配
请实现一个函数用来匹配包括'.'和'*'的正则表达式。模式中的字符'.'表示任意一个字符,而'*'表示它前面的字符可以出现任意次(包含0次)。 在本题中,匹配是指字符串的所有字符匹配整个模式。例如,字符串"aaa"与模式"a.a"和"ab*ac*a"匹配,但是与"aa.a"和"ab*a"均不匹配
/*
思路:只有当模式串和字符串同时等于\0,才可以认为两个串匹配。
在匹配中,对于每个位的匹配可以分为三种情况
1、(相应位匹配||模式串为.&&字符串不是\0)&&模式串下一位是*
2、(相应位匹配||模式串为.&&字符串不是\0)&&模式串下一位不是*
3、相应位不匹配&&(模式位不为.||字符串是\0)
对应1,最复杂。分为*取0,*取1,*>=2三种情况。
*取0对应跳过当前匹配位,继续寻找patter的下一个匹配位,str不变,pattern+2
*取1对应当前匹配位算一次成功匹配,str+1,pattern+2
*取>=2对应一次成功匹配,继续匹配字符串的下一位是否匹配,str+1,pattern不变
三者取或。即只要有一种情况能匹配成功认为字符串就是匹配成功的。
对应2,相当于一次成功匹配,str+1,pattern+1
对应3,匹配失败,直接返回false
*/
class Solution {
public:
bool match(char* str, char* pattern)
{
if(str==NULL||pattern==NULL)
return false;
return matchCore(str,pattern);
}
bool matchCore(char* str, char* pattern)
{
if(*str=='\0'&&*pattern=='\0')
return true;
if(*str!='\0'&&*pattern=='\0')
return false;
if(*(pattern+1)=='*')
{
if(*pattern==*str||(*pattern=='.'&&*str!='\0'))
return matchCore(str+1,pattern+2)||matchCore(str+1,pattern)||matchCore(str,pattern+2);
else
return matchCore(str,pattern+2);
}
if(*str==*pattern||(*pattern=='.'&&*str!='\0'))
return matchCore(str+1,pattern+1);
return false;
}
};
7.把字符串转换成整数
将一个字符串转换成一个整数,要求不能使用字符串转换整数的库函数。
class Solution {
public:
/*
1、首先有可能有正负号,也有可能没有
2、当输入字符串中有非数字的时候输出为0;
*/
int StrToInt(string str)
{
bool g_InvalidValue = false;
if(str.size()<=0)
{
g_InvalidValue = true;
return 0;
}
int i = 0;
int sum = 0;
bool isPositive = false;
if(str[i]=='-')
{
isPositive = true;
i++;
}
else if(str[i]=='+')
{
i++;
}
while(str[i])
{
if(str[i]<='9'&&str[i]>='0')
{
sum = sum*10+str[i]-'0'+0;
}
else
{
g_InvalidValue = true;
return 0;
}
i++;
}
if(isPositive)
sum = -sum;
return sum;
}
};
8.原串翻转
请实现一个算法,在不使用额外数据结构和储存空间的情况下,翻转一个给定的字符串(可以使用单个过程变量)。
给定一个string iniString,请返回一个string,为翻转后的字符串。保证字符串的长度小于等于5000。
测试样例:
"This is nowcoder"
返回:"redocwon si sihT"
class Reverse {
public:
string reverseString(string iniString)
{
// write code here
int length=iniString.size();
int middle=length>>1;//交换时间复杂度O(n);计算次数n/2
if(length<1)
return NULL;
int end=length-1;
for(int i=0;i<=middle,i<=end;i++,end--)
{
int temp=iniString[i];
iniString[i]=iniString[end];
iniString[end]=temp;
}
return iniString;
}
};
9.确定两串乱序同构
给定两个字符串,请编写程序,确定其中一个字符串的字符重新排列后,能否变成另一个字符串。这里规定大小写为不同字符,且考虑字符串重点空格。
给定一个string stringA和一个string stringB,请返回一个bool,代表两串是否重新排列后可相同。保证两串的长度都小于等于5000。
测试样例:
"This is nowcoder","is This nowcoder"
返回:true
"Here you are","Are you here"
返回:false
class Same {
public:
bool checkSam(string stringA, string stringB) {
// write code here
int sizeA=stringA.size();
int sizeB=stringB.size();
int A[256]={0};
int B[256]={0};
if(sizeA!=sizeB)
return false;
for(int i=0;i<sizeA;i++){
A[stringA[i]]++;
B[stringB[i]]++;
}
for(int j=0;j<256;j++){
if(A[j]!=B[j])
return false;
}
return true;
}
};
10.基本字符串压缩
利用字符重复出现的次数,编写一个方法,实现基本的字符串压缩功能。比如,字符串“aabcccccaaa”经压缩会变成“a2b1c5a3”。若压缩后的字符串没有变短,则返回原先的字符串。
给定一个string iniString为待压缩的串(长度小于等于3000),保证串内字符均由大小写英文字母组成,返回一个string,为所求的压缩后或未变化的串。
测试样例
"aabcccccaaa"
返回:"a2b1c5a3"
"welcometonowcoderrrrr"
返回:"welcometonowcoderrrrr"
class Zipper {
public:
string zipString(string iniString) {
// write code here
string s;
for(int i=0;i<iniString.length();i++){
int count=1;
while(i<iniString.length()&&iniString[i]==iniString[i+1])
{
count++;
i++;
}
s+=iniString[i];
s+=to_string(count);
}
if(iniString.length()>s.length()) return s;
return iniString;
}
};
11.翻转子串
题目描述
假定我们都知道非常高效的算法来检查一个单词是否为其他字符串的子串。请将这个算法编写成一个函数,给定两个字符串s1和s2,请编写代码检查s2是否为s1旋转而成,要求只能调用一次检查子串的函数。
给定两个字符串s1,s2,请返回bool值代表s2是否由s1旋转而成。字符串中字符为英文字母和空格,区分大小写,字符串长度小于等于1000。
测试样例:
"Hello world","worldhello "
返回:false
"waterbottle","erbottlewat"
返回:true
/*以s1=ABCD为例,我们先分析s1进行循环移位之后的结果:
ABCD->BCDA->CDAB->DABC->ABCD .......
假设我们把前面移走的数据进行保留:
ABCD->ABCDA->ABCDAB->ABCDABC->ABCDABCD.....
因此看出,对s1做循环移位,所得字符串都将是字符串s1s1的子字符串。如果s2可以由s1循环移位得到,则一定可以在s1s1上。*/
class ReverseEqual {
public:
bool checkReverseEqual(string s1, string s2) {
int size1 = s1.size();
int size2 = s2.size();
if(size1 == 0 || size2 == 0){
return false;
}//if
string str = s1 + s1;
if(str.find(s2) == -1){
return false;
}//if
return true;
}
};
12.单词最近距离
有一篇文章内含多个单词,现给定两个单词,请设计一个高效算法,找出文中这两个单词的最短距离(即最少相隔的单词数,也就是两个单词在文章中位置的差的绝对值)。
给定一个string数组article,代表所给文章,同时给定文章的单词数n和待查找的两个单词x和y。请返回两个单词的最短距离。保证两个单词均在文中出现且不相同,同时保证文章单词数小于等于1000。
class Distance {
public:
int getDistance(vector<string> article, int n, string x, string y) {
// write code here
int p=-1;
int distance = 1000;
int i;
for(i=0;i<article.size();i++){
if(article[i] == x || article[i] == y){
if(p != -1 && article[i] != article[p]){
distance = min(distance,abs(i-p));
}
p = i;
}
}
return distance;
}
};
13.字符串最后一个单词的长度
计算字符串最后一个单词的长度,单词以空格隔开。
输入描述:
一行字符串,非空,长度小于5000。
输出描述:
整数N,最后一个单词的长度。
输入例子:
hello world
输出例子:
5
#include<iostream>
#include<string>
using namespace std;
int main(){
string s;
while(getline(cin,s)){
int i=0;
int flag=1;
int n=0;
for(i=s.length()-1;i>=0;i--){
if(flag && s[i]==' ')
continue;
else if(s[i]!=' '){
flag=0;
++n;
}
else
break;
}
cout << n << endl;
}
}
14.计算字符个数
写出一个程序,接受一个有字母和数字以及空格组成的字符串,和一个字符,然后输出输入字符串中含有该字符的个数。不区分大小写。
输入描述:
输入一个有字母和数字以及空格组成的字符串,和一个字符。
输出描述:
输出输入字符串中含有该字符的个数。
输入例子:
ABCDEF
A
输出例子:
1
#include<iostream>
#include<string>
using namespace std;
int main(){
string s;
char t,t1;
getline(cin,s);
cin>>t;
if(t>=65&&t<=96)
t1=t+32;
if(t>=97&&t<=129)a
t1=t-32;
int i;
int count=0;
for(i=0;i<=s.length();i++){
if(s[i]==t||s[i]==t1)
count++;
}
cout<<count<<endl;
return 0;
}
15.字符个数统计
编写一个函数,计算字符串中含有的不同字符的个数。字符在ACSII码范围内(0~127)。不在范围内的不作统计。
输入描述:
输入N个字符,字符在ACSII码范围内(0~127)。
输出描述:
输出字符的个数。
输入例子:
abc
输出例子:
3
#include<iostream>
using namespace std;
int main(){
char ch;
int arr[128]={0};
int count=0;
while(cin>>ch){
if(ch>=0 && ch<=127){
arr[ch]++;
}
}
for(int i=0;i<128;i++){
if(arr[i]>0)
count++;
}
cout<<count<<endl;
return 0;
}
16.字符串分隔
连续输入字符串,请按长度为8拆分每个字符串后输出到新的字符串数组;
•长度不是8整数倍的字符串请在后面补数字0,空字符串不处理。
输入描述:
连续输入字符串(输入2次,每个字符串长度小于100)
输出描述:
输出到长度为8的新字符串数组
输入例子:
abc
123456789
输出例子:
abc00000
12345678
90000000
#include <stdio.h>
#include <iostream>
#include <string>
using namespace std;
/* 测试数据不止有一组 */
int main()
{
string s1;
string s2 = "0000000";
unsigned int i = 0;
while ( getline(cin, s1) )
{
for (i = 0; i+8 < s1.length(); i=i+8)
{
cout << s1.substr(i, 8) << endl;
}
if (s1.length() - i > 0)
{
cout << s1.substr(i, s1.length() - i) + s2.substr(0, 8-(s1.length() - i))<< endl;
}
}
return 0;
}
17.字符串反转
写出一个程序,接受一个字符串,然后输出该字符串反转后的字符串。例如:
输入描述:
输入N个字符
输出描述:
输出该字符串反转后的字符串
输入例子:
abcd
输出例子:
dcba
#include<iostream>
#include<string>
using namespace std;
int main()
{
string s;
while(getline(cin,s))
{
int length;
length=s.length();
int i;
for(i=0;i<length;i++)
{
cout<<s[length-1-i];
}
cout<<endl;
}
}
18.句子逆序
将一个英文语句以单词为单位逆序排放。例如“I am a boy”,逆序排放后为“boy a am I”
所有单词之间用一个空格隔开,语句中除了英文字母外,不再包含其他字符
接口说明
/**
* 反转句子
*
* @param sentence 原句子
* @return 反转后的句子
*/
public String reverse(String sentence);
输入描述:
将一个英文语句以单词为单位逆序排放。
输出描述:
得到逆序的句子
输入例子:
I am a boy
输出例子:
boy a am I
#include <stdlib.h>
#include <stdio.h>
#include <string.h>
void ReverseWord(char *h,char *r)
{
while(h<r)
{
char tmp=*r;
*r--=*h;
*h++=tmp;
}
}
char *ReverseSentence(char *s)
{
char *p=s;
char *q=s;
//while(q)//Error
while(*q!='\0')
{
if(*q==' ')
{
ReverseWord(p,q-1);
q++;
p=q;
}else
q++;
}
ReverseWord(p,q-1);
ReverseWord(s,q-1);
return s;
}
int main()
{
char s[1000];//gets(s1);gets(s2);
while(gets(s)){
// printf("%s\n",s);
ReverseSentence(s);
printf("%s\n",s);
}
return 0;
}