JZOJ 5111. 【usaco2017_Mar Platinum】Modern Art

来源:互联网 发布:淘宝热线人工服务电话 编辑:程序博客网 时间:2024/05/16 10:00

Description

Art critics worldwide have only recently begun to recognize the creative genius behind the great bovine painter, Picowso.

Picowso paints in a very particular way. She starts with an N×Nblank canvas, represented by an N×N grid of zeros, where a zero indicates an empty cell of the canvas. She then draws N^2 rectangles on the canvas, one in each of N^2 colors (conveniently numbered 1…N^2). For example, she might start by painting a rectangle in color 2, giving this intermediate canvas:

2 2 2 0
2 2 2 0
2 2 2 0
0 0 0 0

She might then paint a rectangle in color 7:

2 2 2 0
2 7 7 7
2 7 7 7
0 0 0 0

And then she might paint a small rectangle in color 3:

2 2 3 0
2 7 3 7
2 7 7 7
0 0 0 0

Each rectangle has sides parallel to the edges of the canvas, and a rectangle could be as large as the entire canvas or as small as a single cell. Each color from 1…N^2 is used exactly once, although later colors might completely cover up some of the earlier colors.

Given the final state of the canvas, please count how many of the N^2 colors could have possibly been the first to be painted.

Input

The first line of input contains N, the size of the canvas (1≤N≤1000). The next N lines describe the final picture of the canvas, each containing N integers that are in the range 0…N^2. The input is guaranteed to have been drawn as described above, by painting successive rectangles in different colors.

Output

Please output a count of the number of colors that could have been drawn first.

Sample Input

4
2 2 3 0
2 7 3 7
2 7 7 7
0 0 0 0

Sample Output

14

Hint

In this example, color 2 could have been the first to be painted. Color 3 clearly had to have been painted after color 7, and color 7 clearly had to have been painted after color 2. Since we don’t see the other colors, we deduce that they also could have been painted first.

Solution

  • 这提示一道英文题,光看懂题就用了就用了不少时间。

  • 题目大意是在一个 NN 的矩阵中,不断加入一个个大小不同、颜色不同的矩阵,(颜色共 NN 种),且后加入的矩阵会覆盖之前的矩阵,

  • 现给出全加入后的最终结果,问哪种颜色的矩阵可能先加入,求满足的颜色数。

  • 我们对每个点进行讨论,求出每个点被多少个矩阵覆盖。

  • 怎么求呢?——用矩阵前缀和!对于一个矩阵:

Solution

  • 之后做一遍矩阵前缀和即可!

  • 对于一个点,如果该点前缀和的值 >1 ,说明被多个矩阵覆盖,则这个点的颜色不可行。

  • 这样把所有不可行的点的颜色都标记后,剩下的颜色就是可行的了,统计答案即可。

  • 特殊情况:全矩阵只有一种颜色,则该颜色不会是最早的,此时答案为: N21

  • 时空复杂度都为 O(N2)

Code

#include<cstdio>using namespace std;const int N=1002;struct data{    int sx,sy,tx,ty;}a[N*N];int n,bz1;int map[N][N],f[N][N];bool ans[N*N];bool bz;inline int read(){    int X=0; char ch=0;    while(ch<'0' || ch>'9') ch=getchar();    while(ch>='0' && ch<='9') X=(X<<3)+(X<<1)+ch-'0',ch=getchar();    return X;}int main(){    n=read();    for(int i=1;i<=n;i++)        for(int j=1;j<=n;j++)        {            map[i][j]=read();            if(map[i][j])            {                if(bz1 && bz1!=map[i][j]) bz=true; else bz1=map[i][j];                if(!a[map[i][j]].sx || i<a[map[i][j]].sx) a[map[i][j]].sx=i;                if(!a[map[i][j]].sy || j<a[map[i][j]].sy) a[map[i][j]].sy=j;                if(i>a[map[i][j]].tx) a[map[i][j]].tx=i;                if(j>a[map[i][j]].ty) a[map[i][j]].ty=j;            }        }    if(!bz)    {        printf("%d",n*n-1);        return 0;    }    for(int i=n*n;i;i--)        if(a[i].tx)        {            f[a[i].sx][a[i].sy]++;            f[a[i].tx+1][a[i].ty+1]++;            f[a[i].sx][a[i].ty+1]--;            f[a[i].tx+1][a[i].sy]--;        }    int sum=n*n;    for(int i=1;i<=n;i++)        for(int j=1;j<=n;j++)        {            f[i][j]+=f[i-1][j]+f[i][j-1]-f[i-1][j-1];            if(f[i][j]>1)            {                if(!ans[map[i][j]]) sum--;                ans[map[i][j]]=true;            }        }    printf("%d",sum);    return 0;}