一:字符串去空格
这道题目是需要清楚空格,那么清除空格后所得到的字符串要比原先的字符串要短,这是我们从头到尾进行清楚空格的话就不会覆盖到空格后面的字符,所以我们可以从头开始清除。
- 设定两个指针p1和p2初始状态都指向字符串首字符。
- 如果p2指向的元素不为空格,那么将p2指向的内容赋值给p1,然后p1和p2指向下一个元素;如果p2指向的内容为空格,那么p2指向下一个元素。
- 直到p2指向字符串末尾的'\0'时清除空格结束。
#include <iostream> #include <stdlib.h> using namespace std; int my_function(char* p) { if (p == NULL) return -1; char * p1 = p; char * p2 = p; while( *p1 != '\0') { if (*p2 !=' ') { *p1 = *p2 ; p2 ++; p1 ++; } else p2 ++; } } int main() { char test[20] = " we are happy! "; cout << test <<endl ; my_function(test); cout << test <<endl ; return 0; }
二:字符串替换
这是道offer上的一道题,思路是从后往前替换空格,这样先遍历一遍字符串的时间复杂度是n,然后最多把n个元素
向前移动,时间复杂度还是n,总的时间复杂度是N.
将长度为1的空格替换为长度为3的“%20”,字符差的产度变长。如果允许我们开辟一个新的数组来存放替换空格后的字符串,那么这道题目就非常简单。设置两个指针分别指向新旧字符串首元素,遍历原字符串,如果碰到空格就在新字符串上填入“%20”,否则就复制元字符串上的内容。但是如果面试官要求在原先的字符串上操作,并且保证原字符串有足够长的空间来存放替换后的字符串,那么我们就得另想方法。
如果从前往后替换字符串,那么保存在空格后面的字符串肯定会被覆盖,那么我们就考虑从后往前进行替换。
- 首先遍历原字符串,找出字符串的长度以及其中的空格数量,
- 根据原字符串的长度和空格的数量我们可以求出最后新字符串的长度。
- 设置两个指针originalIndex和newIndex分别指向原字符串和新字符串的末尾位置。
- 如果originalIndex指向内容不为空格,那么将内容赋值给newIndex指向的位置,如果originalIndex指向为空格,那么从newIndex开始赋值“02%”
- 直到originalIndex==newIndex时表明字符串中的所有空格都已经替换完毕。
#include <iostream> #include <string> using namespace std; int my_replace(char *s, int len) { if(s ==NULL||len ==0) return -1; int p1 = 0 ; int num_black = 0 ; int i = 0; while (s[i] != '\0') { ++p1 ; if(s[i] ==' ') ++num_black; ++ i ; } int p2 = num_black*2 + p1; if (p2 >len) return -2; cout << "p1:" <<p1 <<endl; cout << "p2:" <<p2 <<endl; while(p1>=0 && p2> p1) { //p1遇到遇到空格就替换 if(s[p1]== ' ') { s[p2--] = '0'; s[p2--] = '2'; s[p2--] = '%'; } else //否则把单词半到后面 { s[p2--] = s[p1--]; } -- p1; } return 0; } int main() { char test[100]="we are happy."; cout<<test<<endl;//we are happy. int a =my_replace(test ,100 ); cout << test << endl; return 0; }