您的位置:首页 > 其它

HDU 5583 Kingdom of Black and White(模拟)

2017-09-14 20:18 288 查看
题意:给出一个01串,他的价值就是每段连续的0或者1的个数的平方。现在至多一次机会变换一个位置的0或者1,问能得到最大的价值是多少。

解法:很明显,让大的尽量大,这是一种贪心思想,但是仔细分析发现又不是绝对的,要看答案的贡献度,所以我们采取暴露枚举的方法即可。

首先预处理出每个串的长度。

然后暴力,使得左边-1自己+1,或者右边-1自己+1,看是否可以更新最大值。(注意边界)

最后输出答案即可。

代码如下:

#include <bits/stdc++.h>
using namespace std;
typedef long long ll;
const int maxn = 1e5 + 5;
long long num[maxn];
char str[maxn];

long long Count(int x, int y) {
return (num[x] + 1) * (num[x] + 1) + (num[y] - 1) * (num[y] - 1) - (num[x] * num[x] + num[y] * num[y]);
}

int main() {
#ifndef ONLINE_JUDGE
freopen("in.txt", "r", stdin);
#endif
int T, Case = 1;
scanf("%d",&T);
while(T--) {
memset(num, 0, sizeof(num));
scanf("%s", str);
int len = strlen(str);
int idx = 1;
for(int i = 0, j; i < len; i++) {
long long cnt = 1;
for(j = i + 1; j < len; j++) {
if(str[j] != str[i]) {
break;
}
cnt++;
}
num[idx++] = cnt;
i = j - 1;
}
long long sum = 0;
for(int i = 0; i < idx; i++) {
sum += num[i] * num[i];
}
long long tmp, Max = 0;
for(int i = 1; i < idx; i++) {
if(num[i] >= num[i - 1] && i - 1 > 0) {
if(num[i - 1] == 1) {
tmp = (num[i] + 1 + num[i - 2]) * (num[i] + 1 + num[i - 2]);
tmp -= (num[i] * num[i] + num[i - 2] * num[i - 2] + 1);
} else {
tmp = Count(i, i - 1);
}
if(tmp > Max)
Max = tmp;
}
if(num[i] >= num[i + 1] && i + 1 < idx) {
if(num[i + 1] == 1) {
tmp = (num[i] + 1 + num[i + 2]) * (num[i] + 1 + num[i + 2]);
tmp -= (num[i] * num[i] + num[i + 2] * num[i + 2] + 1);
} else {
tmp = Count(i, i + 1);
}
if(tmp > Max)
Max = tmp;
}
}
printf("Case #%d: %lld\n",Case++, sum + Max);
}
return 0;
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: