88.2005 年11 月金山笔试题。编码完毕以下的处理函数。


函数将字符串中的字符'*'移到串的前部分。前面的非'*'字符后移,但不能改变非'*'字符的先后顺序。函数返回串中字符'*'的数量。如原始串为:ab**cd**e*12,处理后为*****abcde12,函数并返回值为5。(要求使用尽量少的时间和辅助空间)。


思路:使用小标i和j分别来遍历字符串中的*字符和非*字符。

首先使下标j要跳过字符串最后面的非*字符(假设有的话)。然后在while循环里运行这种操作:移动j到当前位置的下一个非*字符处,移动过程中记录经过的*个数,移动i到当前位置的下一个*字符处,交换j,i处字符,反复上面的操作直到遍历到字符串起始位置。

C++代码:

#include<iostream>
using namespace std;
namespace MS100P_88
{
	int  strMove(char* str)
	{
		int i = strlen(str)-1;	//i遍历字符串中的*
		int j = i;				//j遍历字符串中的非*字符
		int count = 0;
		while (j > 0 && str[j] != '*') j--;  //跳过最后面的非'*'字符
		while (j >= 0&&i>=0)				
		{
			while (str[i] != '*'&&i >= 0)
			i--;
			while (str[j] == '*'&&j >=0)
			{
				j--;
				count++;
			}
			str[i--] = str[j];
			str[j--] = '*';
		}
		return count;
	}
	void test()
	{
		char str[] = "ab**cd**e*12";
		cout << str << endl;
		cout << "num of * is: " << strMove(str) << endl;
		cout << str << endl;
	}
}
int _tmain(int argc, _TCHAR* argv[])
{
	MS100P_88::test();
	return 0;
}

执行结果: