poj-3276 Face The Right Way白书

Face The Right Way

题目大意:给你一个字符串,包含B,F,两种字母,然后每次可以连续翻转K个,问每次翻转几个,就是问一个值,可以翻转最少次数,使字符串全部变为F

思路:刚开始,一看这么简单,遍历1-n的K,枚举不就行了,呵呵呵,md肯定TLE,每枚举一次,时间复杂度大概是O(2^n) n最大5000 2000ms大概是10的9次方,也就是2的32次方左右,肯定超时,

如果是对于同一个区间的话,翻转两次 == 没有翻转 ,如果是我们只需要求,有多少个区间需要翻转不就好了,然后如果从最左端开始,如果最左这个需要翻转,那么我们就翻转从当前到后面共K个,然后下一个再下一个,但是每次翻转,都会循环K次,这里有了技巧,如果我们拿过来一个数组,f[i] 如果是1就是代表从i到后面k个都翻转,是0就是不翻转,就不要循环了,具体讲解写注释里面了,更清楚一些。

#include <iostream>
#include <cstring>

using namespace std;

char arr[5555]; //多余的不用管
int f[5555]; //上述,
int dir[5555]; //用整型数组表示字符串,0就是F 1就是B
int n;

int dfs(int k)
{
	int res = 0, sum = 0; //sum很重要
	memset(f, 0, sizeof f);
	for(int i = 0; i + k <= n; ++i) //从i到后面i+k-1是翻转区间 一共k个
	{
		if((dir[i] + sum) % 2 != 0)
		  //什么意思呢,刚开始sum0对吧,如果dir[i]是1的话就是B,代表需要翻转
		  //
		{
			res++; //翻转一次+1
			f[i] = 1; //当前区间标记为翻转
		}
		sum += f[i];
		//既然从i -- i+k-1都翻转了,那么从i+1到i+k-1都是翻了的,这样的话,
		//sum + 1 这里1就是f[i] 就是翻的时候,这样sum是1对吧,
		//然后后面dir[i]本来是0的就要变成1对吧,但是咱又不想循环,这样当前for循环到
		//下个i的时候,会判断dir[i] + sum 因为翻转了,sum是1 对于后面的如果dir[i]是0
		//这时候加起来是1 就能代表需要翻转了,sum的作用就是用了代理翻转,记录一下
		if(i - k + 1 >= 0)
			sum -= f[i-k+1];
		//这里又很重要,对于一个i看他翻转了没是不是要看它前面隔了k个的那个,
		//sum只能管到一个i到前面k个,那当前循环完了下一个i就不会被之前那个sum
		//管到了,那么就得减去之前的翻转情况,自己模拟一下就知道了
	}
	for(int i = n-k+1; i < n; ++i)
	{
		if((dir[i] + sum) % 2 != 0) return -1; 
		//对于后面k-1个是不会作为区间第一个翻转的,前面的都保证了是F 所以看这几个
		//有B就不行-1
		if(i - k + 1 >= 0)
		{
			sum -= f[i-k+1]; //同上
		}
	}
	return res;
}



int main()
{
	cin >> n;
	for(int i = 0; i < n; ++i) 
	{
		char ch;
		cin >> ch;
		if(ch == 'B') dir[i] = 1; //初始化
		else dir[i] = 0;
	}
	int ans = 0x3f3f3f3f;
	int temp;
	for(int k = 1; k <= n; ++k) //遍历所有的k,求最小值
	{
		int a = dfs(k); //返回值就是当前k要满足最后条件需要翻转的最小次数
		if(a < ans && a != -1) 
		{
			temp = k;
			ans = a;
		}
	}
	cout << temp << ' ' << ans << endl;
	return 0;
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值