将一个字符串中的字符替换成另一个字符串

来源:互联网 发布:香港有淘宝网吗 编辑:程序博客网 时间:2024/03/28 20:36

题目:原地实现字符串中的每个空格替换成"%20",例如输入"We are happy", 输出"We%20are%20happy"

被替换的字符串当然不仅仅是空格,上面只是个例子

这是道很好的题目,也是我进百度面试时的一道题,题目不难,但是问题得考虑全面

#include <iostream>#include <vector>#include <cassert>using namespace std;int findNumberFirst(const char *str, const char *dest, vector<int>& pvec){if (str == NULL || dest == NULL)return 0;int pos = 0;int lenStr = strlen(str);int lenDest = strlen(dest);if (lenStr < lenDest)return 0;int count = 0;while (pos <= lenStr - lenDest){if (strncmp(str + pos, dest, strlen(dest)) == 0){pvec.push_back(pos);pos += lenDest;count++;}else{pos++;}}return count;}int findNumberLast(const char *str, const char *dest, vector<int> &pvec){if (str == NULL || dest == NULL)return 0;int strLen = strlen(str);int destLen = strlen(dest);if (strLen < destLen)return 0;int pos = 0;while (pos <= strLen - destLen){if (strncmp(str + pos, dest, strlen(dest)) == 0){pos += destLen;pvec.push_back(pos - 1);}else{pos++;}}return pvec.size();}void replaceArray(char *str, const char *src, const char *dest){if (str == NULL || src == NULL || dest == NULL)return;vector<int> pvec;int strLen = strlen(str);int srcLen = strlen(src);int destLen = strlen(dest);if (strLen < srcLen)return;int posBefore = 0;int posAfter = 0;if (srcLen < destLen){int count = findNumberLast(str, src, pvec);if (count <= 0)return;posAfter = strLen + count * (destLen - srcLen) - 1;posBefore = strLen - 1;while (count > 0 && posBefore >= 0){if (pvec[count - 1] == posBefore){posAfter -= destLen;strncpy(str + posAfter + 1, dest, strlen(dest));count--;posBefore--;}else{str[posAfter--] = str[posBefore--];}}}else if (strLen > destLen){int count = findNumberFirst(str, src, pvec);if (count <= 0)return;posAfter = 0;posBefore = 0;int i = 0;while (count >= 0 && posBefore < strLen){if (count > 0 && pvec[i] == posBefore){strncpy(str + posAfter, dest, strlen(dest));posAfter += destLen;count--;posBefore += srcLen;i++;}else{str[posAfter++] = str[posBefore++];}}str[posAfter] = '\0';}}void main(){char *str = new char[100];if (str == NULL)return;memset(str, '\0', 100);const char *src = " ";const char *dest = "%20";//case1: 只有1个空格strcpy(str, " ");replaceArray(str, src, dest);cout << "str: " << str << endl;replaceArray(str, dest, src);cout << "str: " << str << endl;//case2: 两个空格strcpy(str, "  ");replaceArray(str, src, dest);cout << "str: " << str << endl;replaceArray(str, dest, src);cout << "str: " << str << endl;//case3: 正常情况strcpy(str, "we are happy");replaceArray(str, src, dest);cout << "str: " << str << endl;replaceArray(str, dest, src);cout << "str: " << str << endl;//case3: 空格在前strcpy(str, " we are happy");replaceArray(str, src, dest);cout << "str: " << str << endl;replaceArray(str, dest, src);cout << "str: " << str << endl;//case4: 空格在后strcpy(str, "we are happy ");replaceArray(str, src, dest);cout << "str: " << str << endl;replaceArray(str, dest, src);cout << "str: " << str << endl;//case4: 没空格strcpy(str, "wearehappy");replaceArray(str, src, dest);cout << "str: " << str << endl;replaceArray(str, dest, src);cout << "str: " << str << endl;//case5: 两边一样strcpy(str, "we are happy");replaceArray(str, src, dest);cout << "str: " << str << endl;src = "%20";assert(dest == "%20");replaceArray(str, dest, src);cout << "str: " << str << endl;}


很有意思的一个情况是srcLen和destLen或大或小的情形,其边界条件的判定不一样

比如we are happy为例子,从后往前拷贝时,count=2

在count=0时,恰好将最前面的空格替换完成,we则不用重复拷贝

但是对于从前往后拷贝

当count=0时,最后面的happy将不会被拷贝

原创粉丝点击