说实话,看了半天也没看出来这是让干什么的,上网一搜,才知道是dfs,完全没看出来???,哎,真是菜的抠脚啊。。
还是应该多多刷题。。。
#include<bits/stdc++.h>
using namespace std;
#define ll long long
int a[]= {2,5,9,11,16,17,19,21, 22, 24, 26, 30,31,33,35,36,41,50,52 };
int vis[154];
int mp[160][160];
void tianman(int x,int y,int len,int num)///把每个正方形对应区域都设为该正方形的边长
{
for(int i=x; i<x+len; i++)
{
for(int j=y; j<y+len; j++)
{
mp[i][j]=num;
}
}
}
bool solve()///判断154*154这个区域是否都已经填满满,即用到了所有边长的正方形。
{
for(int i=1; i<=154; i++)
{
for(int j=1; j<=154; j++)
{
if(mp[i][j]==0)
{
return 0;
}
}
}
return 1;
}
bool judge(int x,int y,int num)
{
if(x+num>155||y+num>155) ///注意边界的判定
{
return 0;
}
for(int i=x; i<x+num; i++)
{
for(int j=y; j<y+num; j++)
{
if(mp[i][j]!=0)
{
return 0;
}
}
}
return 1;
}
int dfs(int x,int y)
{
if(solve())
{
return 1;
}
else
{
int flag=1;
for(int i=1; i<=154&&flag; i++)
{
for(int j=1; j<=154&&flag; j++)
{
if(mp[i][j]==0)
{
x=i;
y=j;
flag=0;
}
}
}
for(int i=0; i<=18; i++)
{
if(judge(x,y,a[i]))///判断即将要覆盖的这个区域是否全为空,若果全为空,则可以放a[i]
{
if(vis[i]==0)
{
vis[i]=1;
tianman(x,y,a[i],a[i]);
if(dfs(x,y+a[i])) ///从x,y+a[i] 开始下一次递归
{
return 1;
}
tianman(x,y,a[i],0);
vis[i]=0;
}
}
else ///如果a[k]放不下,那么以后的数字也放不下
break;
}
}
return 0;
}
int main()
{
memset(vis,0,sizeof(vis));
memset(mp,0,sizeof(mp));
tianman(1,1,47,47);
tianman(1,48,46,46);
tianman(1,94,61,61);
int ans=0;
dfs(1,1);
for(int j=1; j<=154; j++)
{
if(ans!=mp[154][j])
{
ans=mp[154][j];
printf("%d\n",ans);
}
}
// printf("50 33 30 41\n"); ///答案
return 0;
}