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;  

}  

 

你可能感兴趣的:(ZOJ)