#include<iostream>
#include<cstdio>
#include<cstring>
#include<map>
#include<set>
#include<algorithm>
using namespace std;
const int maxn=1009;
int c[maxn];
int m[maxn][maxn];
int L[maxn][maxn],R[maxn][maxn],U[maxn][maxn],D[maxn][maxn];
int n;
struct P
{
int flag,v;
bool operator<(const P y)const
{
if(v!=y.v)
return v<y.v;
return flag>0;
}
}p[maxn*2];
int e;
struct bit
{
int lowbit(int x)
{
return x&-x;
}
void init()
{
memset(c,0,sizeof(c));
}
int sum(int x)
{
int res=0;
for(int i=x;i>0;i-=lowbit(i))
{
res+=c[i];
}
return res;
}
void add(int x,int a)
{
for(int i=x;i<maxn;i+=lowbit(i))
{
c[i]+=a;
}
}
}my;
void clear(int n)
{
for(int i=1;i<=n;i++)
{
for(int j=1;j<=n;j++)
{
L[i][j]=U[i][j]=R[i][j]=D[i][j]=0;
}
}
}
void pre()
{
for(int i=1;i<=n;i++)
{
for(int j=1;j<=n;j++)
{
if(U[i][j])
{
U[i][j]+=U[i-1][j];
}
if(L[i][j])
{
L[i][j]+=L[i][j-1];
}
}
}
for(int i=n;i>0;i--)
{
for(int j=n;j>0;j--)
{
if(D[i][j])
{
D[i][j]+=D[i+1][j];
}
if(R[i][j])
{
R[i][j]+=R[i][j+1];
}
}
}
}
int solve(int x,int type)
{
e=0;
for(int i=1;i+x<=n;i++)
{
if(type&&m[i][i+x])
{
p[e].flag=i+x-min(L[i][i+x],U[i][i+x])+1;
p[e].v=i+x;
e++;
p[e].flag=-(i+x);
p[e].v=i+x+min(R[i][i+x],D[i][i+x])-1;
e++;
}
else if(!type&&m[i+x][i])
{
p[e].flag=i+x-min(L[i+x][i],U[i+x][i])+1;
p[e].v=i+x;
e++;
p[e].flag=-(i+x);
p[e].v=i+x+min(R[i+x][i],D[i+x][i])-1;
e++;
}
}
my.init();
sort(p,p+e);
int now=0,res=0;
for(int i=0;i<e;i++)
{
if(p[i].flag>0)
{
res-=my.sum(p[i].v);
my.add(p[i].flag,1);
}
else
{
res+=my.sum(-p[i].flag);
}
}
return res;
}
int main()
{
int ca,id=0;
scanf("%d",&ca);
while(ca--)
{
scanf("%d",&n);
clear(n);
int res=0;
for(int i=1;i<=n;i++)
{
for(int j=1;j<=n;j++)
{
scanf("%d",&m[i][j]);
if(m[i][j]==1)
{
L[i][j]=U[i][j]=R[i][j]=D[i][j]=1;
}
}
}
pre();
res+=solve(0,1);
for(int i=1;i<n;i++)
{
res+=solve(i,1);
res+=solve(i,0);
}
printf("Case %d: %d\n",++id,res);
}
}
HDU4331 Image Recognition 树状数组+扫描线
最新推荐文章于 2024-07-30 12:06:53 发布