程序编程——001字符串旋转

      今天是2014.06.16,从今天开始,我将参看july的博客进行算法的学习及练习,在此只是做一个记录。

————————————分割线—————————————————————————————————————————————


001 字符串旋转


描述:

       定义字符串的向左旋转的操作:把一个字符串的前面若干个字符移动到字符串的尾部,如abcde将前两个字符移动到尾部,则有cdeab。

       实现字符串左旋函数,对长度为n的字符串的时间复杂度为O(n),空间复杂度为O(1)。


解法:

方案一:暴力法:硬移,即一位一位的移动,时间复杂度O(m*n),空间复杂度O(1)。

void leftShitOne(char *s,int n)
{
	char t = s[0];
	for(int i=1;i<n;i++)
	{
		s[i-1]=s[i];
	}
	s[n-1] = t;
}

void votate1(char *s, int n, int m)
{;
	for(int i=0;i<m;i++)
	{
		leftShitOne(s,n);
	}
}
方案二:将n个字符分成n/m取天棚段,如果n/m是整数,则将前m个字符向后移动n/m位即可,否则,先将前m个字符向后移动n/m位,然后依次将剩下的n%m个字符与这m个字符进行移位。时间复杂度O(n),空间复杂度O(1)。

void votate2(string &str,int m)
{
	if(str.length()==0 || m < 0)
		return;
	int p1=0,p2=m;
	int n = str.length();
	int k = (n-m)-n%m;
	while(k--)
	{
		swap(str[p1],str[p2]);
		p1++;
		p2++;
	}
	int r = n-p2;
	while(r--)
	{
		int i=p2;
		while(i>p1)
		{
			swap(str[i],str[i-1]);
			i--;
		}
		p1++;
		p2++;
	}
}

方案三:散步反转法,将字符串分成两个部分,前m个字符和后n-m个字符,先对前m个字符进行翻转,在对后n-m个字符进行翻转,最后对整个字符串进行翻转

void reverse(string &str,int start,int end)
{
	while(start<end)
	{
		swap(str[start],str[end]);
		start++;
		end--;
	}
}

void votate3(string &str,int m)
{
	int n = str.length();
	reverse(str,0,m-1);
	reverse(str,m,n-1);
	reverse(str,0,n-1);
}


相似题型:

1.编写程序,在原字符串中把字符串尾部的m个字符移动到字符串的头部,要求:长度为n的字符串操作时间复杂度为O(n),空间复杂度为O(1)。 例如,原字符串为”Ilovebaofeng”,m=7,输出结果为:”baofengIlove”。

解决方案:与左旋相似,三步翻转法

2.单词翻转。输入一个英文句子,翻转句子中单词的顺序,但单词内字符的顺序不变,句子中单词以空格符隔开。为简单起见,标点符号和普通字母一样处理。例如,输入“I am a student.”,则输出“student. a am I”。

解决方案:以空格为分界,对每个单词进行翻转,然后翻转整个句子。



评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值