字符串操作——面试题总结

摘录于下, 来源: http://rjwyr.blog.163.com/blog/static/112986400201153061911864/

字符串操作  

  1. #include <iostream>  
  2. #include <sstream>  
  3. #include <limits>  
  4. #include <vector>  
  5. #include <string>  
  6. using namespace std;  

/*\

1.翻转句子中的单词

题目:输入一个英文句子,翻转句子中单词的顺序,但单词内字符的顺序不变。
句子中单词以空格符隔开。为简单起见,标点符号和普通字母一样处理。
例如输入“I am a student.”,则输出“student. a am I”。
使用: reverse_iterator
*/
  1. */  
  2. void reverseWord()  
  3. {  
  4. vector<string> vec;  
  5. /* string str,word; 
  6. getline(cin,str); 
  7. istringstream in_str(str); 
  8. while(in_str>>word)vec.push_back(word); 
  9. */  
  10. string word;  
  11. while(cin>>word)  
  12. vec.push_back(word);  
  13. vector<string>::reverse_iterator it;/************************/  
  14. for(it=vec.rbegin();it!=vec.rend();it++)  
  15. cout<<*it<<" ";  
  16. cout<<endl;  
  17. }  
  18. /*  
/*

2.第一个只出现一次的字符

例如abcaccd 输出b
解题思路:利用hash思想,字符一共256个,则建立一个大小为256的数字
*/
  1. int getFirstNoRepeatCh()  
  2. {  
  3. char str[256];  
  4. int s[256],i;  
  5. cout<<"please input the word:";  
  6. cin>>str;  
  7. for(i=0;i<256;i++)  
  8. s[i]=0;  
  9. for(i=0;str[i]!='\0';i++)  
  10. s[str[i]]++;  
  11. for(i=0;str[i]!='\0';i++)  
  12. {  
  13. if(s[str[i]]==1)  
  14. {  
  15. cout<<str[i]<<endl;  
  16. return i;  
  17. }  
  18. }  
  19. return 0;  
  20. }  

/*

3.把字符串转化为数字

题目不难,但是考察编程习惯,比如判断正负号,是否为数字字符,是否越界等
函数返回值指示是否正确转化,sum代表转化后的值
*/
  1. bool converseToNumber(const char *pStr, int &sum)  
  2. {  
  3. const char *pChar=pStr;  
  4. int flag=1;  
  5. bool isValid=true;  
  6. __int64 s=0;  
  7. if(pStr==NULL)  
  8. return false;  
  9. if(*pChar=='-')  
  10. {  
  11. flag=-1;  
  12. pChar++;  
  13. }  
  14. else  
  15. {  
  16. if(*pChar=='+')  
  17. pChar++;  
  18. }  
  19. while(*pChar != '\0')  
  20. {  
  21. if( *pChar <='9' && *pChar>='0')  
  22. {  
  23. s=10*s+ (*pChar -'0');  
  24. //overflow  
  25. if(s > std::numeric_limits <int>::max())  
  26. {  
  27. isValid=false;  
  28. s=0;  
  29. break;  
  30. }  
  31. }  
  32. //the char is not a digit,input error  
  33. else  
  34. {  
  35. isValid=false;  
  36. s=0;  
  37. break;  
  38. }  
  39. }  
  40. if(*pChar == '\0')  
  41. {  
  42. if(flag<0)  
  43. s=0-s;  
  44. sum=static_cast<int>(s);  
  45. }  
  46. return isValid;  
  47. }  

/*

4.左旋字符串

定义字符串的左旋转操作:把字符串前面的若干个字符移动到字符串的尾部。如把字符串abcdef左旋转2位得到字符串cdefab。
请实现字符串左旋转的函数。要求时间对长度为n的字符串操作的复杂度为O(n),辅助内存为O(1)。
*/
/*
思路1,将字符串看成两部分XY,目标是YX,我们利用将X Y 分别翻转来得到结果 (XT YT)T=YX.
*/

  1. //reverse the word  
  2. void reverse(char *pStart,char *pEnd)  
  3. {  
  4. char ch;  
  5. if(pStart!=NULL && pEnd!=NULL)  
  6. {  
  7. while(pStart<pEnd)  
  8. {  
  9. ch=*pStart;  
  10. *pStart=*pEnd;  
  11. *pEnd=ch;  
  12. pStart++;  
  13. pEnd--;  
  14. }  
  15.   
  16.   
  17. }  
  18. }  
  19. char * leftConverseStr(char *pStr,int m)  
  20. {  
  21. if(pStr!=NULL)  
  22. {  
  23. int len=static_cast<int>(strlen(pStr));  
  24. if(len>0 && m<len && m>0)  
  25. {  
  26. char *pFirstS=pStr;  
  27. char *pFirstE=pStr+m-1;  
  28. char *pSecondS=pStr+m;  
  29. char *pSecondE=pStr+len-1;  
  30. reverse(pFirstS,pFirstE);  
  31. reverse(pSecondS,pSecondE);  
  32. reverse(pFirstS,pSecondE);  
  33. }  
  34. }  
  35. return pStr;  
  36. }  

/*

5.在字符串中删除特定的字符.

输入They are students.”和”aeiou”,则删除之后的第一个字符串变成”Thy r stdnts.”。
遍历源字符串,对每个字符在第二个字符串中查找是否存在,存在则删除。首先我们对第一部分进行优化,由于删除一个字符时,后面的都要
往前移,这样删除一个字符需要O(n),太耗时了,一个改进的做法是维护两个指针 pFast pSlow,当当前字符是需要删除的字符时,pFast ++
,是不需要删除的字符时,两个都++,这样我们最后得到了pslow就是结果,对于查找部分,利用hash,时间复杂度O(1).
*/
 
  1. char * delChar(char *pSource,char *pDel)  
  2. {  
  3. char hashT[256];  
  4. memset(hashT,0,sizeof(hashT));  
  5. char *pChar=pDel;  
  6. while(*pChar!='\0')  
  7. {  
  8. hashT[*pChar]=1;  
  9. pChar++;  
  10. }  
  11. char *pFast=pSource,*pSlow=pSource;  
  12. while(*pFast != '\0')  
  13. {  
  14. if(hashT[*pFast] != 1)  
  15. {  
  16. *pSlow=*pFast;  
  17. pSlow++;  
  18. }  
  19. pFast++;  
  20. }  
  21. *pSlow='\0';  
  22. return pSource;  
  23. }  

/*

6.对称子字符串的最大长度

题目:输入一个字符串,输出该字符串中对称的子字符串的最大长度。
比如输入字符串“google”,由于该字符串里最长的对称子字符串是“goog”,因此输出4。
解题思路:判断一个字符串是否对称相信都会做,从两边向中间开始逐一判断,如果采用这个思路,我们需要枚举出所有可能的子串
即n^2个,然后对每一个子串判断是否对称,这样时间复杂度O(n^3).因为存在重复判断,所以时间负责度会这么高,我们换一种思路
从中间像两端判断,这样可以降低复杂度,为O(n^2)
*/
 
  1. int getLongestSymmetricalLength(char *pStr)  
  2. {  
  3. int len=0;  
  4. if(pStr!=NULL)  
  5. {  
  6. int tmp=0;  
  7. len=1;  
  8. char *pChar=pStr;  
  9. while(*pChar != '\0')  
  10. {  
  11. //odd length  
  12. char *pLeft=pChar-1;  
  13. char *pRight=pChar+1;  
  14. while(pLeft >= pStr && *pRight!= '\0' && (*pLeft==*pRight))  
  15. {  
  16. pLeft--;  
  17. pRight++;  
  18. }  
  19. tmp=pRight-pLeft-1;  
  20. if(tmp>len)  
  21. len=tmp;  
  22. pLeft=pChar;  
  23. pRight=pChar+1;  
  24. while(pLeft >=pStr && *pRight!='\0' && (*pLeft==*pRight))  
  25. {  
  26. pLeft--;  
  27. pRight++;  
  28. }  
  29. //even length  
  30. tmp=pRight-pLeft-1;  
  31. if(tmp>len)  
  32. len=tmp;  
  33. pChar++;  
  34. }  
  35. }  
  36. return len;  
  37.   
  38.   
  39. }  
  40. int main()  
  41. {  
  42. // reverseWord();  
  43. // getFirstNoRepeatCh();  
  44. /* 
  45. cout<<"please input the converseStr :"; 
  46. char str[100]; 
  47. int sum=0; 
  48. cin>>str; 
  49. if(converseToNumber(str,sum)) 
  50. cout<<sum<<endl; 
  51. else 
  52. cout<<"invalid input,converse error"<<endl; 
  53. */  
  54. /* 
  55. cout<<"please input the leftConverseStr :"; 
  56. char str[100]; 
  57. int m=5; 
  58. cin>>str; 
  59. char * re=leftConverseStr(str,3); 
  60. cout<<re<<endl; 
  61. */  
  62. /* cout<<"please input the source and del string :"; 
  63. char source[100],del[100]; 
  64. // cin>>source>>del; 
  65. cin.getline(source,100,'\n'); 
  66. cin.getline(del,100,'\n'); 
  67. char *re=delChar(source,del); 
  68. cout<<re<<endl; 
  69. */  
  70. char str[100];  
  71. cout<<"please input the string :";  
  72. cin>>str;  
  73. int re=getLongestSymmetricalLength(str);  
  74. cout<<re<<endl;  
  75. return 0;  
  76. }  
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值