zoukankan      html  css  js  c++  java
  • BZOJ3736 : [Pa2013]Karty

    显然只需要考虑与障碍点相邻的格子,通过旋转坐标系,可以只考虑障碍点在格子上方的情况。

    悬线法求出每个点往上的最长延伸距离$x$,以及往左往右的延伸距离$y$。

    那么当$rgeq x$时,$c$至多为$y$。

    特别地,当某个点下方也是障碍点的时候,$r$不能超过$x$。

    维护出每个$r$对应的最大的$c$即可。

    时间复杂度$O(nm)$。

    #include<cstdio>
    #include<algorithm>
    const int N=2505;
    int n,m,i,j,k,l[N],r[N],h[N],f[N],ans,pos;char a[N][N],b[N][N];
    inline void up(int&a,int b){a>b?(a=b):0;}
    void work(int n,int m,int rev){
      int i,j,k,x,y;
      for(i=1;i<=m;i++)l[i]=1,r[i]=m,h[i]=0,a[n+1][j]='_';
      for(i=1;i<=n;i++){
        for(j=k=1;j<=m;j++)if(a[i][j]=='X'){
          h[j]++;
          if(k>l[j])l[j]=k;
        }else h[j]=0,l[j]=1,r[j]=m,k=j+1;
        for(j=k=m;j;j--)if(a[i][j]=='X'){
          up(r[j],k);
          x=h[j],y=r[j]-l[j]+1;
          if(rev){
            up(f[y+1],x-1);
            if(a[i+1][j]=='_')up(f[1],x);
          }else{
            up(f[x],y);
            if(a[i+1][j]=='_')f[x+1]=0;
          }
        }else k=j-1;
      }
    }
    int main(){
      scanf("%d%d",&n,&m);
      for(i=1;i<=n;i++)scanf("%s",a[i]+1),f[i]=m;
      for(i=0;i<4;i++){
        work(n,m,i&1);
        for(j=1;j<=n;j++)for(k=1;k<=m;k++)b[k][n-j+1]=a[j][k];
        std::swap(n,m);
        for(j=1;j<=n;j++)for(k=1;k<=m;k++)a[j][k]=b[j][k];
      }
      for(i=1;i<=n;i++){
        if(i>1)up(f[i],f[i-1]);
        if(i*f[i]>ans)ans=i*f[i],pos=i;
      }
      return printf("%d %d",pos,ans/pos),0;
    }
    

      

  • 相关阅读:
    poj 1579(动态规划初探之记忆化搜索)
    hdu 1133(卡特兰数变形)
    CodeForces 625A Guest From the Past
    CodeForces 625D Finals in arithmetic
    CDOJ 1268 Open the lightings
    HDU 4008 Parent and son
    HDU 4044 GeoDefense
    HDU 4169 UVALive 5741 Wealthy Family
    HDU 3452 Bonsai
    HDU 3586 Information Disturbing
  • 原文地址:https://www.cnblogs.com/clrs97/p/7492608.html
Copyright © 2011-2022 走看看