C - You Are Given a WASD-string... CodeForces - 1202C


#include <bits/stdc++.h> using namespace std; typedef long long ll; const int maxn=2e5+100; char s[maxn]; /* 这个字符不是随便可以加的,因为会出现,你加了一个字符 使左边的最小值往右边移了一下,但是导致最右边往右移了,得不偿失 首先我们考虑垂直方向,我们假设它在0这个位置,那么他所移动的 位置就是差值为1的点,我们在一个位置前面加了W,那么他后面所有点的坐标都加一 如果你在一个位置前加了s,那么他后面的所有点的坐标会减一, 你要保证可以减小,那么你加一的时候,后面不能有最大值,并且前面不能有最小值 减一的时候后面的不能有最小值,并且前面不能有最大值,否则都不可以 所以要找那种,可以加的情况,就是加了可以减少,不会增加也不会不变的那种 因为垂直和水平情况一样,我们只考虑一边 我们必须明确你要加一,那么后面的全部加一,你要减一那么后面的全部减一 垂直 假如它达到了很多次最大值和很多次最小值 1、当最后一个最大值在第一个最小值前面的时候,我们只要将后面的值加一,最小值减少 而你改其他的位置,要么会使值变大,要么会使值不变 2、当最后一次最小值出现在第一个最大值之前时,只要将最小值后面的减一,那么值也会变小 其他两种情况改了和没改一样,或者造成变大 */ int len; ll maxlast,maxfirst,minlast,minfirst; int work(char c,char c1) { maxlast=maxfirst=minlast=minfirst=0; ll max_=0,min_=0; ll y=0; for(int i=0; i<len; i++) { if(s[i]==c) y++; else if(s[i]==c1) y--; if(max_<y) { maxlast=maxfirst=i; max_=y; } else if(y==max_) { maxlast=i; } if(y<min_) { minlast=minfirst=i; min_=y; } else if(y==min_) { minlast=i; } } return (max_-min_+1); } int main() { int t; scanf("%d",&t); while(t--) { scanf("%s",s); len=strlen(s); int flag=0,flag1=0; ll n=work('W','S'); if((maxlast<minfirst||maxfirst>minlast)&&n>2) flag=1; ll m=work('A','D'); if((maxlast<minfirst||maxfirst>minlast)&&m>2) flag1=1; ll ans=n*m; if(flag&&flag1)ans=min(n*(m-1),m*(n-1)); else if(flag)ans=(n-1)*m; else if(flag1) ans=(m-1)*n; printf("%lld\n",ans); } return 0; }

猜你喜欢

转载自www.cnblogs.com/zhangzhenjun/p/11708116.html