【剑指offer】替换空格

题目:要求写一个函数,将字符串中的空格替换为%20,样例:“i like flower”转换成“i%20like%20flower”,要求时间复杂度为O(n)。

       在网络编程中,如果URL参数中有特殊字符,如空格,“#”等,可能导致服务器端无法获得正确的参数值,我们需要将这些特殊符号转换为服务器可以识别的字符。转换规则为:“%”后面跟上ASCII码的两位十六进制的表示,比如空格的ASCII码是32,即十六进制的0x20,因此空格被替换为“%20”,同理可得“#”被替换为“%23”。

       很直观的,我们首先会想到的做法就是从头开始扫描字符串,每次遇到空格就进行替换,然后把空格后面所有字符向后移动两个字节,这样才不会使后面的字符被覆盖,移动过程可以形象地用下图表示。

                         

       假设字符串长度为n,对每个空格字符,需要移动后面的O(n)个字符,因此对于含有O(n)个空格字符的字符串而言,总的时间效率为O(n^{\2}),但是这样的时间复杂度太大了。我们可以换一种思路,先遍历一次字符串,统计空格总数并计算替换后字符串长度,最后其长度为原来长度加上2乘以空格数目,然后从字符串后面开始复制与替换。

                       

       如上图所示,我们准备两个指针p1,p2,让p1指向原始字符串的末尾,而p2指向替换后的字符串的末尾,向前移动p1,把它指向的字符复制到p2指向的位置,直到碰到空格为止。当遇到空格之后,p1先前移动一格,p2向前移动3格且插入“%20”,然后再接着向前复制,直到p1与p2指向同一位置,表明所有空格都已替换完毕。此方法中所有字符只移动一次,因此时间复杂度为O(n),比第一种思路要快,下面是我的完整代码,如有错误,还请指出。

#include <stdio.h>
#include <stdlib.h>

void ReplaceBlank(char string[], int len)
{
	int i = 0;
	int orglen = 0;
	int numblank = 0;
	int newlen = 0;
	if (string == NULL && len <= 0)
		return;
	while (string[i]!='\0')
	{
		++orglen;
		if (string[i] == ' ')
		{
			++numblank;
		}
		++i;
	}
	newlen = orglen + numblank * 2;
	if (newlen > len)
		return;
	int indexoforg = orglen;
	int indexofnew = newlen;
	while (indexoforg >= 0 && indexofnew > indexoforg)
	{
		if (string[indexoforg] == ' ')
		{
			string[indexofnew--] = '0';
			string[indexofnew--] = '2';
			string[indexofnew--] = '%';
		}
		else
		{
			string[indexofnew--] = string[indexoforg];
		}
		--indexoforg;
	}
}

int main()
{
	char arr[20] = "i like flower";
	int len = sizeof(arr) / sizeof(arr[0]);
	ReplaceBlank(arr, len);
	printf("%s\n", arr);
	system("pause");
	return 0;
}

 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值