zoj 2067 White Rectangles

这题解决的算法处理,真的很难想清楚!!尤其是最后的正矩形如何处理。不过终于看懂了

#include<stdio.h>
#include<stdlib.h>
#include<string.h>
#include<limits.h>
#define MAX 110 
#define min(a,b) ((a)<(b))?(a):(b)
char board[MAX][MAX];  
int sum[MAX][MAX];  
  
int main(void)  
{  

  int n,i,ans,j,len,k;  
  while(scanf("%d",&n)!=EOF)  
  {  
    memset(sum,0,sizeof(sum)); /*初始化每个点的个数为0*/ 
    memset(board,'#',sizeof(board));  /*棋盘的初始都为#*/
    getchar(); /*接收回车 */ 
    for(i=1;i<=n;++i)  
      gets(board[i]+1);/*将棋牌字符串放入这个board矩阵中  */
  
         ans=0;  
  
        for(i=1;i<=n;++i)  /*取出矩阵的字符进行设置 */
            for(j=1;j<=n;++j)  
                if(board[i][j]=='.')  
                {  
                    if(board[i][j-1]!='.')  /*如何前面不是.*/
                        sum[i][j]=1;  /*这是第i,j就是单独的点*/ 
                    else  /*如何使连续.*/ 
                        sum[i][j]=sum[i][j-1]+1;  /*自己加上墙壁上点的个数*/ 
                }  
  
        for( i=1;i<=n;++i)  
            for( j=1;j<=n;++j)  
            {  
                len=INT_MAX;  
                for(k=i;k<=n && sum[k][j];++k)  /*从第i行一下所有的行数,第j列对应的每一行中最短的矩形个数,并且该点有值*/
                {          /*当该点的顶部满足条件,且该点也满足条件则最后的矩形大小由小的部分决定(即下面的点)*/ 
                    len=min(len,sum[k][j]);  /*取和小的部分就是求正矩形部分,在以i行为顶边的矩形,len=以k,j为坐标的矩形个数*/ 
                    ans+=len;  
                }  
            }  
        printf("%d\n",ans);  
  }  
  
  return 0;  
}  

 

posted @ 2014-03-25 13:28  keyboard3  阅读(300)  评论(0编辑  收藏  举报