您的位置:首页 > 其它

蓝桥杯 剪邮票 (DFS+BFS)

2018-03-28 21:36 239 查看
剪邮票

如【图1.jpg】,
有12张连在一起的12生肖的邮票。
现在你要从中剪下5张来,要求必须是连着的。
(仅仅连接一个角不算相连)
比如,【图2.jpg】,【图3.jpg】中,粉红色所示部分就是合格的剪取。
请你计算,一共有多少种不同的剪取方法。
请填写表示方案数目的整数。
注意:你提交的应该是一个整数,不要填写任何多余的内容或说明性文字。







思路很直接,先是排列组合问题,用深搜找出12个数里5个不重样的组合,然后转化成求面积问题,用广搜检查面积是否为5,是则输出

#include <iostream>
#include <queue>
using namespace std;
struct Node
{
int x;
int y;
Node(int nx, int ny)
{
x = nx;
y = ny;
}
};
int dir[4][2] = { -1,0,1,0,0,-1,0,1 };
int ans;
bool book[13];
int num[5];
bool BFSLegal()
{
queue<Node> q;
int sum = 0;
int visit[3][4];
int index = 0;
memset(visit, -1, sizeof(visit));
for (int i = 0;i < 3;i++)
{
bool flag = false;
for (int j = 0;j < 4;j++)
{
sum++;
if (sum == num[index])
{
if (index == 0)
{
q.push(Node(i, j));
visit[i][j] = 1;
index++;
}
else
{
visit[i][j] = 0;
index++;
}
}
if (index == 5) { flag = true; break; }
}
if (flag)break;
}
sum = 1;
while (q.size() != 0)
{
Node n = q.front();
q.pop();
for (int i = 0;i < 4;i++)
{
int tx=n.x+dir[i][0], ty=n.y+dir[i][1];
if (tx < 0 || tx >= 3 || ty < 0 || ty >= 4)continue;
if (visit[tx][ty]==0)
{
q.push(Node(tx,ty));
visit[tx][ty] = 1;
sum++;
}
}
}
return sum==5;
}
void DFS(int deepth)
{
if (deepth == 5)
{
if (BFSLegal())
{
ans ++ ;
}
}
else
{
for (int i = 1;i <= 12;i++)
{
if (book[i]&&i>=num[deepth-1])  //不重样
{
num[deepth] = i;
book[i] = false;
DFS(deepth + 1);
book[i] = true;
}
}
}
}
int main()
{
ans = 0;
memset(book, true, sizeof(book));
DFS(0);
cout << ans;
return 0;
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: