这题很容易可以转换模型,把操作一转换为纵坐标改变一个小于2*(l-1)的偶数的值,操作二转换为横纵坐标同时改变一个小于(l-1)的值。
然后贪心处理。
容易想到操作二最多进行一次,所以只要枚举是否进行操作二然后取最大值就可以了。
有一个问题要注意,当操作二改变的值为(l-2)时,可能要再次改变一次(l-1)答案最优,此时可以转换为向右上角走一步然后用操作一走,步数都是两步。
然后就是高精度除法的问题。
可以考虑二分商然后判断。
但是因为这题卡了时间,所以没过。
#include<cstdio> #include<cstring> #include<algorithm> #define ll long long #define mo 1000000000 #pragma GCC optimize(3) #define N 80 using namespace std; ll T,i,bzp,p[N*10],len,sum,lp,mi[20]; char ch[N]; ll div(ll x,ll y){ if (x%y==0) return x/y; return x/y+1; } struct bignum{ ll x[N],len; }n,m,l,ans,ans1,temp,mx,L,R,mid,ansp,l2,l_1; ll pd(bignum a,bignum b){ ll i; if (a.len<b.len) return 1; if (a.len>b.len) return 0; for (i=a.len;i>=1;i--){ if (a.x[i]<b.x[i]) return 1; if (a.x[i]>b.x[i]) return 0; } return 0; } void swap1(bignum &a,bignum &b){ temp=a; a=b; b=temp; } bignum add(bignum a,bignum b){ ll i; if (pd(a,b)) swap1(a,b); for (i=1;i<=a.len;i++){ a.x[i]+=b.x[i]; a.x[i+1]+=a.x[i]/mo; a.x[i]%=mo; } while (a.x[a.len+1]) a.len++; return a; } bignum add1(bignum a,ll b){ ll k=1; a.x[1]+=b; while (a.x[k]>=mo){ a.x[k+1]+=a.x[k]/mo; a.x[k]%=mo; k++; } while (a.x[a.len+1]) a.len++; return a; } bignum sub(bignum a,bignum b){ ll i; for (i=1;i<=a.len;i++){ a.x[i]-=b.x[i]; if (a.x[i]<0) a.x[i]+=mo,a.x[i+1]--; } while (a.x[a.len]==0) a.len--; return a; } bignum sub1(bignum a,ll b){ ll k=1; a.x[1]-=b; while (a.x[k]<0){ a.x[k]+=mo; a.x[k+1]--; k++; } while (a.x[a.len]==0) a.len--; return a; } ll mod(bignum a,ll k){ return a.x[1]%k; } void write(bignum a){ ll i,j,n,x; printf("%lld",a.x[a.len]); for (i=a.len-1;i>=1;i--){ x=a.x[i]; n=0; while (x){ n++; x/=10; } for (j=1;j<=9-n;j++) printf("0"); printf("%lld",a.x[i]); } printf(" "); } bignum mul(bignum a,bignum b){ ll i,j; for (i=0;i<=temp.len;i++) temp.x[i]=0; temp.len=a.len+b.len-1; for (i=1;i<=a.len;i++){ for (j=1;j<=b.len;j++){ temp.x[i+j-1]+=a.x[i]*b.x[j]; temp.x[i+j]+=temp.x[i+j-1]/mo; temp.x[i+j-1]%=mo; } } while (temp.x[temp.len+1]) temp.len++; return temp; } bignum div1(bignum a,ll b){ ll i,r=0; for (i=a.len;i>=1;i--){ r=r*mo+a.x[i]; a.x[i]=r/b; r=r%b; } while (a.x[a.len]==0) a.len--; return a; } bignum div(bignum a,bignum b){ ll i; for (i=0;i<=L.len;i++) L.x[i]=0; for (i=0;i<=ansp.len;i++) ansp.x[i]=0; L.len=1;L.x[1]=1; R=a; while (pd(R,L)==0){ mid=div1(add(L,R),2); if (pd(mul(mid,b),a)) L=add1(mid,1); else{ R=sub1(mid,1); ansp=mid; } } return ansp; } int main(){ freopen("move.in","r",stdin); freopen("move.out","w",stdout); scanf("%lld",&T); mx.len=N-1; for (i=1;i<N;i++) mx.x[i]=mo-1; mi[0]=1; for (i=1;i<=10;i++) mi[i]=mi[i-1]*10; while (T--){ memset(n.x,0,sizeof(n.x)); memset(m.x,0,sizeof(m.x)); memset(l.x,0,sizeof(l.x)); n.len=m.len=l.len=0; scanf("%s",ch+1); bzp=0; if (ch[1]=='-') bzp=1; len=strlen(ch+1)-bzp; for (i=bzp+1;i<=strlen(ch+1);i++) if (ch[i]!='-') p[i-bzp]=ch[strlen(ch+1)-i+1+bzp]-'0'; sum=0; lp=0; for (i=1;i<=len;i++){ lp++; sum=p[i]*mi[lp-1]+sum; if (lp==9){ n.len++; n.x[n.len]=sum; lp=0; sum=0; } } if (lp){ n.len++; n.x[n.len]=sum; } scanf("%s",ch+1); bzp=0; if (ch[1]=='-') bzp=1; len=strlen(ch+1)-bzp; for (i=bzp+1;i<=strlen(ch+1);i++) if (ch[i]!='-') p[i-bzp]=ch[strlen(ch+1)-i+1+bzp]-'0'; sum=0; lp=0; for (i=1;i<=len;i++){ lp++; sum=p[i]*mi[lp-1]+sum; if (lp==9){ m.len++; m.x[m.len]=sum; lp=0; sum=0; } } if (lp){ m.len++; m.x[m.len]=sum; } scanf("%s",ch+1); bzp=0; if (ch[1]=='-') bzp=1; len=strlen(ch+1)-bzp; for (i=bzp+1;i<=strlen(ch+1);i++) if (ch[i]!='-') p[i-bzp]=ch[strlen(ch+1)-i+1+bzp]-'0'; sum=0; lp=0; for (i=1;i<=len;i++){ lp++; sum=p[i]*mi[lp-1]+sum; if (lp==9){ l.len++; l.x[l.len]=sum; lp=0; sum=0; } } if (lp){ l.len++; l.x[l.len]=sum; } if (pd(n,m)) swap1(n,m); if (mod(n,2)!=mod(m,2)){ printf("Poor MLG! "); continue; } ans=ans1=mx; l=sub1(l,1); l2=add(l,l); l_1=sub1(l,1); if (pd(l,m)==0){ ans=add1(div(sub(n,m),l2),1); write(ans); continue; } if (mod(n,2)==1){ if (pd(m,add(l,sub1(l,1)))==0) ans1=add(div(add1(n,1),l2),div(add1(m,1),l2)); if (mod(l,2)==1) ans=add1(add(div(sub(n,l),l2),div(sub(m,l),l2)),1); else ans=add1(add(div(sub(n,l_1),l2),div(sub(m,l_1),l2)),1); } else{ ans1=add(div(n,l2),div(m,l2)); if (mod(l,2)==0) ans=add1(add(div(sub(n,l),l2),div(sub(m,l),l2)),1); else ans=add1(add(div(sub(n,l_1),l2),div(sub(m,l_1),l2)),1); //write(sub(n,l));write(l2); //write(div(sub(n,l),l2)); } if (pd(ans1,ans)) write(ans1); else write(ans); } return 0; }