feat: 汉诺塔问题

This commit is contained in:
LouisFonda 2025-03-08 00:50:45 +08:00
parent 40a676cd31
commit b2e8377e3d
Signed by: yigencong
GPG Key ID: 29CE877CED00E966

View File

@ -0,0 +1,43 @@
/**
有三根柱子分别命名为 ABCA 上有若干个盘子盘子的大小不等且每个盘子都可以放在另一根柱子上要求从柱子 A 上将所有盘子移动到柱子 C 且必须遵守以下规则
一次只能移动一个盘子
每次移动时盘子只能从柱子顶部移动且一个盘子不能放在比它小的盘子上
目标是使用柱子 B 作为辅助柱子最少移动次数将盘子从柱子 A 移动到柱子 C
*/
/**
*
* @param {number} n 汉诺塔问题的规模
* 思路假设我们只有两个盘子只需要把小盘子移动到B柱上再把大盘子移动到C柱子上最后把小盘子从B柱移动到C柱子我们把问题做一个抽象假设有三个盘子因为要想移动
* 大盘子就必须把它上面的所有小盘子移动到B住上去之后才能把这个大盘子移动到C柱至于怎么移动我不管
*
* 分析假设现在有三个盘子第一步我们发现底部的盘子无法直接移动把问题抽象为移动n-1个盘子在这里就是移动上面的两个盘子之后会发现第二个盘子也移不动所以再把问题抽象为
* (n-1)-1,也就是移动第一个盘子第一个盘子可以直接移动这样就可以把第一个盘子移动到B上第二个盘子移动到C,......
*/
function towerOfHanoi(n) {
// 将n个盘子从A借助B移动到C
howToMove(n, 'A', 'C', 'B');
}
/**
* @param {*} n 要移动的所有盘子
* @param {*} from 初始位置
* @param {*} to 目标位置
* @param {*} aux 辅助柱
*/
function howToMove(n, from, to, aux) {
// 如果只有一个盘子那就直接移动到目标位置即可(这也是递归结束的条件)
if (n === 1) {
console.log(`${n}${from} 移动到 ${to}`);
return;
}
// 1.移动n-1个盘子因为如果不把所有的小盘子移动到辅助位置大盘子就不可能移动到目标位置
howToMove(n - 1, from, aux, to);
// 2.将大盘子移动到目标位置
console.log(`${n}${from} 移动到 ${to}`);
// 3.将剩下的所有盘子从辅助位置移动到目标位置
howToMove(n - 1, aux, to, from);
}
towerOfHanoi(3);