博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
P1242 新汉诺塔
阅读量:5110 次
发布时间:2019-06-13

本文共 1300 字,大约阅读时间需要 4 分钟。

题目描述

设有n个大小不等的中空圆盘,按从小到大的顺序从1到n编号。将这n个圆盘任意的迭套在三根立柱上,立柱的编号分别为A、B、C,这个状态称为初始状态。

现在要求找到一种步数最少的移动方案,使得从初始状态转变为目标状态。

移动时有如下要求:

·一次只能移一个盘;

·不允许把大盘移到小盘上面。

输入输出格式

输入格式:

文件第一行是状态中圆盘总数;

第二到第四行分别是初始状态中A、B、C柱上圆盘的个数和从上到下每个圆盘的编号;

第五到第七行分别是目标状态中A、B、C柱上圆盘的个数和从上到下每个圆盘的编号。

输出格式:

每行一步移动方案,格式为:move I from P to Q

最后一行输出最少的步数。

输入输出样例

输入样例#1: 
53 3 2 12 5 401 23 5 4 31 1
输出样例#1: 
move 1 from A to Bmove 2 from A to Cmove 1 from B to Cmove 3 from A to Bmove 1 from C to Bmove 2 from C to Amove 1 from B to C7

说明

圆盘总数≤45

每行的圆盘描述是从下到上的圆盘编号

 

Solution:

  最近太蠢了,打了个爆搜,爆$0$`~`。。。

  正解思路实在是巧妙,我们处理出每个盘的起始位置和目标位置,然后贪心的想到,我们应该从大到小让盘依次移到目标位置,移动过程中就是让小盘让路(即移到另一个中间盘上),然后每次就层层递归,输出就好了。(怎么会有这么巧的思路~)

代码:

 

#include
#define il inline#define For(i,a,b) for(int (i)=(a);(i)<=(b);(i)++)#define Bor(i,a,b) for(int (i)=(b);(i)>=(a);(i)--)using namespace std;const int N=55;int n,fr[N],to[N],ans;string s="ABC";il void dfs(int u,int v){ if(fr[u]==v)return; Bor(i,1,u-1) dfs(i,6-fr[u]-v); printf("move %d from %c to %c\n",u,s[fr[u]-1],s[v-1]); fr[u]=v,ans++;}int main(){ cin>>n; int t,x; For(i,1,3){ cin>>t; while(t--)cin>>x,fr[x]=i; } For(i,1,3){ cin>>t; while(t--)cin>>x,to[x]=i; } Bor(i,1,n) dfs(i,to[i]); cout<

 

 

 

 

转载于:https://www.cnblogs.com/five20/p/9138583.html

你可能感兴趣的文章
怎么保存退出vi编辑
查看>>
项目优化之热更新
查看>>
执行带返回参数的存储过程
查看>>
ECNUOJ 2616 游黄山
查看>>
Linux 查询配置命令
查看>>
存储过程入门
查看>>
Java泛型的基本使用
查看>>
我的游戏学习日志8——数字游戏策划(3)数字游戏的概念
查看>>
智力逻辑题
查看>>
Phpcms V9导航循环下拉菜单的调用技巧
查看>>
SpringBoot前后端分离Instant时间戳自定义解析
查看>>
开发一个简单的 Vue 弹窗组件
查看>>
1076 Wifi密码 (15 分)
查看>>
rsync
查看>>
java中的IO操作总结
查看>>
noip模拟赛 党
查看>>
bzoj2038 [2009国家集训队]小Z的袜子(hose)
查看>>
Java反射机制及其Class类浅析
查看>>
Postman-----如何导入和导出
查看>>
面试题17:合并两个排序的链表
查看>>