2005 NPSC F. P方陣
作法 : 舉出所有子區域
並在檢查的時候 減少不可能的搜尋條件
/*************************************************************/
#include <stdlib.h>
#include <stdio.h>
int input()
{
char cha;
int x=0;
while(cha=getchar())
if(cha!=' '&&cha!='\n') break;
x=cha-48;
while(cha=getchar())
{
if(cha==' '||cha=='\n') break;
x=x*10+cha-48;
}
return x;
}
main()
{
int t,time=0,A,B;
scanf("%d",&t);
while(t--)
{
scanf("%d %d",&A,&B);
int a,b,c,e;
int map[101][101]={0};
for(a=1;a<=A;a++)
for(b=1;b<=B;b++)
map[a][b]=input();
int p=(A>B)?A:B;
int NxN[101]={0};
for(a=1;a<=A;a++) /*固定X*/
for(b=1;b<=B;b++) /*固定Y*/
{
for(c=1;c<=p;c++) /*延伸N*/
{
if(c+a>A||c+b>B) break;
int t1,t2;
int find=0;
for(t1=a;t1<=a+c&&find==0;t1++)
{
int appearx[101]={0};
for(t2=b;t2<=b+c&&find==0;t2++)
{
appearx[map[t1][t2]]++;
if(appearx[map[t1][t2]]==2) find=1;
if(map[t1][t2]>c+1) {find=1;c=map[t1][t2]-2;}
}
}
if(find==0)
for(t2=b;t2<=b+c&&find==0;t2++)
{
int appeary[101]={0};
for(t1=a;t1<=a+c&&find==0;t1++)
{
appeary[map[t1][t2]]++;
if(appeary[map[t1][t2]]==2) find=1;
if(map[t1][t2]>c+1) {find=1;c=map[t1][t2]-2;}
}
}
if(find==0)
NxN[c+1]++;
}
}
printf("Page #%d:\n",++time);
int find=0;
for(a=2;a<=p;a++)
if(NxN[a]!=0)
{
printf("%dx%d P-square: appear %d time(s).\n",a,a,NxN[a]);
find=1;
}
if(find==0) {printf("No P-square exists.\n");}
}
return 0;
}