NOIP——jzoj 2250

题目描述
你知道New Orange Industry Palatable公司吗?这是老板Smart为了与苹果公司竞争而新开的一家橘子公司,它的业务是栽培美味的橘子并售卖,公司简称为NOIP。 NOIP公司新推出N+1个橘子,每个橘子上都贴有一个标签,其中有N个普通的橘子上面印有一个”N”或”O”或”I”字母。还有一个独一无二的幸运橘子标签印有”P”字母。 NOIP公司搞了一个优惠活动,把N个普通橘子排成一排,从左到右依次编号为1~N。让顾客从左到右选三个橘子,如果依次排列组成了”NOI”,就可获得优惠券。Smart想把贴有标签P的幸运橘插入到排列中的(可以插入到队列的任意位置)。在换取优惠券时,P橘子可以作为N橘子或O橘子或I橘子使用。Smart想知道加入P橘子以后,第一个选购的顾客最多有多少种选法可以得到优惠券。

输入

第一行是一个整数N,表示NOIP公司有N个普通橘子。
第二行是一个长度为N的字符串S,仅由N,O,I三个大写英文字母组成。字符串的左数第i个字母表示第i个橘子的标签类型。

输出

输出为一行,表示选择方式的最大值。

样例输入

样例输入1
5
NOIOI

样例输入2
7
NNNOIII

样例输出

样例输出1
6

样例输出2
18

【样例说明】
样例1中将”P”放在”NOIOI”中”N”前一个位置或后一个位置,并将”P”作为N橘子使用,最多有6种选法可以得到优惠券。
样例2中将”P”放在” NNNOIII “中”O”前一个位置或后一个位置,并将”P”作为O橘子使用,最多有18种选法可以得到优惠券。

数据范围限制

30%的数据:3≤N≤20;
60%的数据:3≤N≤200;
80%的数据:3≤N≤3000;
100%的数据:3≤N≤100000。

题解:用前缀和的方法来求。

代码:

include

include

include

include

include

include

using namespace std;
int n,f[3][100001];
long long tot=0,a,b,c,d;
char s[100001];
int main()
{
freopen(“noip.in”,”r”,stdin);
freopen(“noip.out”,”w”,stdout);
scanf(“%d”,&n);
for (int i=1;i<=n;i++)
{
cin>>s[i];
if (s[i]==’N’) f[0][i]=f[0][i-1]+1;else f[0][i]=f[0][i-1];
if (s[i]==’O’) f[1][i]=f[1][i-1]+1;else f[1][i]=f[1][i-1];
if (s[i]==’I’) f[2][i]=f[2][i-1]+1;else f[2][i]=f[2][i-1];
}
for (int i=1;i<=n;i++)
{
if (s[i]==’N’) a+=f[1][n]-f[1][i];
if (s[i]==’O’) b+=f[0][i]*(f[2][n]-f[2][i]);
if (s[i]==’I’) c+=f[1][i];
d=d>f[0][i-1](f[2][n]-f[2][i-1])?d:f[0][i-1](f[2][n]-f[2][i-1]);
}
tot=max(c,d);
tot=max(tot,a);
printf(“%lld”,tot+b);
fclose(stdin);fclose(stdout);
return 0;
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值