问题 A: Kingdom of Black and White
时间限制: 1 Sec 内存限制: 64 MB提交: 13 解决: 7
[ 提交][ 状态][ 讨论版]
题目描述
In the Kingdom of Black and White (KBW), there are two kinds of mice: black mouse and white mouse.
Now N mice are standing in a line, some of them are black, the others are white. The total strength of those mice are calculated by dividing the line into minimum parts, each part should still be continuous, and can only contain one kind of mouse. Then the strength is the sum of the squared length for each part.
However, an old, evil witch comes, and tells the mice that she will change the color of at most one mouse and thus the strength of those mice might change.
The mice wonder the maximum possible strength after the witch finishes her job.
Now N mice are standing in a line, some of them are black, the others are white. The total strength of those mice are calculated by dividing the line into minimum parts, each part should still be continuous, and can only contain one kind of mouse. Then the strength is the sum of the squared length for each part.
However, an old, evil witch comes, and tells the mice that she will change the color of at most one mouse and thus the strength of those mice might change.
The mice wonder the maximum possible strength after the witch finishes her job.
输入
First line contains an integer T, which indicates the number of test cases.
Every test case only contains a string with length N, including only 0 (representing a black mouse) and 1 (representing a white mouse).
⋅ 1≤T≤50.
⋅ for 60% data, 1≤N≤1000.
⋅ for 100% data, 1≤N≤10 5.
⋅ the string only contains 0 and 1.
Every test case only contains a string with length N, including only 0 (representing a black mouse) and 1 (representing a white mouse).
⋅ 1≤T≤50.
⋅ for 60% data, 1≤N≤1000.
⋅ for 100% data, 1≤N≤10 5.
⋅ the string only contains 0 and 1.
输出
For every test case, you should output "Case #x: y",where x indicates the case number and counts from 1 and y is the answer.
样例输入
2
000011
0101
样例输出
Case #1: 26
Case #2: 10
提示
思路:
好吧好吧,根本就不用线段树啊,NND,傻了,随便看一下就知道合并方法能分成两类,分开讨论就可以,wa了一次是在counter=1的地方没有处理好,一定要注意这种边界条件
啊
#include <iostream>
#include <cstring>
#include <cstdio>
#include <cmath>
using namespace std;
typedef unsigned long long ull;
const int maxn=100000+10;
int counter,num[maxn];
long long maximum;
ull max(ull a,ull b)
{
if(a>b) return a;
else return b;
}
struct node
{
int l;
int r;
long long sum;
}nodes[4*maxn];
void buildtree(int s,int e,int index)
{
nodes[index].l=s;
nodes[index].r=e;
if(s==e) {nodes[index].sum=num[s]*num[s]; return;}
int m=(s+e)/2;
buildtree(s,m,2*index);
buildtree(m+1,e,2*index+1);
nodes[index].sum=nodes[2*index].sum+nodes[2*index+1].sum;
}
long long query(int s,int e,int index)
{
if(e<s) return 0;
if(s==nodes[index].l&&e==nodes[index].r) return nodes[index].sum;
int m=(nodes[index].l+nodes[index].r)/2;
if(e<=m) return query(s,e,2*index);
else if(s>=m+1) return query(s,e,2*index+1);
else return query(s,m,2*index)+query(m+1,e,2*index+1);
}
int main(int argc, const char * argv[]) {
//freopen("/Users/zhangjiatao/Documents/ACM/input.txt","r",stdin);
int T;
scanf("%d",&T);
for(int t=1;t<=T;t++)
{
string a;
cin>>a;
int temp=0;
counter=0;
maximum=-1;
for(int i=0;i<a.size();i++)
{
temp++;
if(a[i]!=a[i+1]||i==a.size()-1)
{
counter++;
num[counter]=temp;
temp=0;
}
}
if(counter==1) { printf("Case #%d: %lld\n",t,(long long)num[1]*num[1]); continue;}
buildtree(1,counter,1);
for(int i=1;i<=counter-1;i++)
{
long long tot=0;
if(num[i+1]==1&&i+2<=counter)
{
int l1=num[i];
int l2=num[i+2];
tot+=query(1,i-1,1);
tot+=query(i+3,counter,1);
tot+=(l1+1+l2)*(l1+1+l2);
}
else
{
int l1=max(num[i],num[i+1]);
int l2=min(num[i],num[i+1]);
tot+=(l1+1)*(l1+1)+(l2-1)*(l2-1);
tot+=query(1,i-1,1);
tot+=query(i+2,counter,1);
}
maximum=max(tot,maximum);
}
printf("Case #%d: %lld\n",t,maximum);
}
return 0;
}