面试题4:替换空格
题目:请实现一个函数,把字符串中的每个空格替换成"%20"。例如输入“We are happy.”,则输出“We%20are%20happy.”。
❖ 时间复杂度为O(n2)的解法,不足以拿到Offer
最直观的做法是从头到尾扫描字符串,每一次碰到空格字符的时候做替换。由于是把1个字符替换成3个字符,我们必须要把空格后面所有的字符都后移两个字节,否则就有两个字符被覆盖了。
代码如下:
#include <iostream>
using namespace std;//length为string的实际长度(不包括'\0')
void ReplaceBlank(char string[], int length)
{if (string == nullptr && length <= 0) return;int p = length + 2;int q = 0;while (q <= p){if (string[q] == ' '){for (int i = p; i >= q + 3; i--)string[i] = string[i - 2];string[q] = '%';string[q + 1] = '2';string[q + 2] = '0';p += 2;}q++;}
}int main()
{char string[50] = "We are happy.";ReplaceBlank(string, 13);cout << string << endl;return 0;
}
❖ 时间复杂度为O(n)的解法,搞定Offer就靠它了
我们可以先遍历一次字符串,这样就能统计出字符串中空格的总数,并可以由此计算出替换之后的字符串的总长度。每替换一个空格,长度增加2,因此替换以后字符串的长度等于原来的长度加上 2 乘以空格数目。我们还是以前面的字符串"We are happy."为例,"We are happy."这个字符串的长度是14 (包括结尾符号’\0’),里面有两个空格,因此替换之后字符串的长度是18。
从后往前把字符串中的空格替换成“%20”的过程:
代码如下:
#include <iostream>
using namespace std;//length为字符串数组string的总容量
void ReplaceBlank(char string[], int length)
{if (string == nullptr && length <= 0) return;int originalLength = 0;//字符串string的实际长度int numberOfBlank = 0;int i = 0;while (string[i] != '\0'){++originalLength;if (string[i] == ' ')++numberOfBlank;++i;}int newLength = originalLength + numberOfBlank * 2;if (newLength > length) return;int indexOfOrignal = originalLength;int indexOfNew = newLength;while (indexOfOrignal >= 0 && indexOfNew > indexOfOrignal){if (string[indexOfOrignal] == ' '){string[indexOfNew--] = '0';string[indexOfNew--] = '2';string[indexOfNew--] = '%';}else{string[indexOfNew--] = string[indexOfOrignal];}--indexOfOrignal;}
}int main()
{char string[50] = "We are happy.";ReplaceBlank(string, 50);cout << string << endl;return 0;
}
测试用例:
● 输入的字符串中包含空格(空格位于字符串的最前面,空格位于字符串的最后面,空格位于字符串的中间,字符串中有连续多个空格)。
● 输入的字符串中没有空格。
● 特殊输入测试(字符串是个 NULL 指针、字符串是个空字符串、字符串只有一个空格字符、字符串中只有连续多个空格)。
本题考点:
● 考查对字符串的编程能力。
● 考查分析时间效率的能力。我们要能清晰地分析出两种不同方法的时间效率各是多少。
● 考查对内存覆盖是否有高度的警惕。在分析得知字符串会变长之后,我们能够意识到潜在的问题,并主动和面试官沟通以寻找问题的解决方案。
● 考查思维能力。在从前到后替换的思路被面试官否定之后,我们能迅速想到从后往前替换的方法,这是解决此题的关键。