#!/bin/bash - #=============================================================================== # # FILE: Hanoi_tower.sh # # USAGE: ./Hanoi_tower.sh # # DESCRIPTION: # # OPTIONS: --- # REQUIREMENTS: --- # BUGS: --- # NOTES: --- # AUTHOR: Francis Drake K (), 772523354@qq.com # ORGANIZATION: M33 # CREATED: 2018年08月16日 20:04 # REVISION: --- #=============================================================================== tower_1=() tower_2=() tower_3=() step=(0) level_up=() create_tower () { for (( CNTR=0; CNTR<$1; CNTR+=1 )); do tower_1=( ${tower_1[*]} `echo "$CNTR+1" |bc ` ) done } # ---------- end of function create_tower ---------- #--- FUNCTION ---------------------------------------------------------------- # NAME: mv_to_tower3 # DESCRIPTION: 将标准塔移动到tower3 # PARAMETERS: tower_name() # RETURNS: #------------------------------------------------------------------------------- mv_to_tower3 () { if [ ${tower_3[*]} -ne 0 ] ; then # 若是塔中有元素则更新目标塔 update_to_tower fi # 将参数数组(起始塔)的最上层元素(数组的下标0位置的数据)赋值给塔3的最上层元素 tower_3[0]= ${$1[0]} # 删除参数数组(起始塔)的最上层元素 unset ${$1[0]} # 更新起始塔(将数组中的所有元素所有下标-1) update_from_tower $1 # 将元素,起始塔,目标塔当作参数传入count_step count_step ${$1[0]} $1 tower_3 } # ---------- end of function mv_to_tower3 ---------- mv_to_tower2 () { if [ ${tower_2[*]} -ne 0 ] ; then # 若是塔中有元素则更新目标塔 update_to_tower fi # 将参数数组(起始塔)的最上层元素(数组的下标0位置的数据)赋值给塔3的最上层元素 tower_2[0]= ${$1[0]} # 删除参数数组(起始塔)的最上层元素 unset ${$1[0]} # 更新起始塔(将数组中的所有元素所有下标-1) update_from_tower $1 # 将元素,起始塔,目标塔当作参数传入count_step count_step ${$1[0]} $1 tower_2 } # ---------- end of function mv_to_tower2 ---------- mv_to_tower1 () { if [ ${tower_1[*]} -ne 0 ] ; then # 若是塔中有元素则更新目标塔 update_to_tower fi # 将参数数组(起始塔)的最上层元素(数组的下标0位置的数据)赋值给塔3的最上层元素 tower_1[0]= ${$1[0]} # 删除参数数组(起始塔)的最上层元素 unset ${$1[0]} # 更新起始塔(将数组中的所有元素所有下标-1) update_from_tower $1 # 将元素,起始塔,目标塔当作参数传入count_step count_step ${$1[0]} $1 tower_2 } # ---------- end of function mv_to_tower1 ---------- #--- FUNCTION ---------------------------------------------------------------- # NAME: update_tower # DESCRIPTION: 更新起始塔(数组) # PARAMETERS: tower_name # RETURNS: #------------------------------------------------------------------------------- update_from_tower () { for (( CNTR=1; CNTR<${$1[*]}; CNTR+=1 )); do ${$1[$CNTR-1]}= ${$1[$CNTR]} done } # ---------- end of function update_tower ---------- #--- FUNCTION ---------------------------------------------------------------- # NAME: update_to_tower # DESCRIPTION: 更新目标塔(数组) # PARAMETERS: tower——name # RETURNS: #------------------------------------------------------------------------------- update_to_tower () { for (( CNTR=0; CNTR<${$1[*]}; CNTR+=1 )); do ${$1[$CNTR+1]}= ${$1[$CNTR]} unset ${$1[0]} done } # ---------- end of function update_to_tower ---------- #--- FUNCTION ---------------------------------------------------------------- # NAME: count_step # DESCRIPTION: 记录起始塔,移动数,目标塔到step()中 # PARAMETERS: # RETURNS: #------------------------------------------------------------------------------- count_step () { lev=`echo "L$1"` tower_from=$2 tower_to=$3 step=(${step[*]} `echo "$lev $tower_from $tower_to"` ) } # ---------- end of function count_step ---------- #--- FUNCTION ---------------------------------------------------------------- # NAME: 3_level_tower_to # DESCRIPTION: 初始化level_up()将三阶汉诺塔从塔1移动到塔3的方法存入 # PARAMETERS: # RETURNS: #------------------------------------------------------------------------------- 3_level_tower_to () { level_up=(${level_up[*]} echo 'mv_to_tower3 tower_1') # L1从塔1移动到塔3 level_up=(${level_up[*]} echo 'mv_to_tower2 tower_1') # L2从塔1移动到塔2 level_up=(${level_up[*]} echo ' mv_to_tower2 tower_3') # L1从塔1移动到塔2 level_up=(${level_up[*]} echo 'mv_to_tower3 tower_3') # L3从塔1移动到塔3 level_up=(${level_up[*]} echo 'mv_to_tower1 tower_2') # L1从塔1移动到塔1 level_up=(${level_up[*]} echo 'mv_to_tower3 tower_2') # L2从塔1移动到塔3 level_up=(${level_up[*]} echo 'mv_to_tower3 tower_1') # L1从塔1移动到塔3 }# ---------- end of function 3_level_tower_to ---------- #--- FUNCTION ---------------------------------------------------------------- # NAME: 3_level_tower_back # DESCRIPTION: 三阶汉诺塔从塔3移动到塔1 # PARAMETERS: # RETURNS: #------------------------------------------------------------------------------- # 3_level_tower_back () # { # mv_to_tower1 tower_3 # L1从塔3移动到塔1 # mv_to_tower2 tower_3 # L2从塔3移动到塔2 # mv_to_tower2 tower_1 # L1从塔1移动到塔2 # mv_to_tower1 tower_3 # L3从塔3移动到塔1 # mv_to_tower3 tower_2 # L1从塔2移动到塔3 # mv_to_tower1 tower_2 # L2从塔2移动到塔1 # mv_to_tower1 tower_3 # L1从塔3移动到塔1 # } # ---------- end of function 3_level_tower_back ---------- #--- FUNCTION ---------------------------------------------------------------- # NAME: change_num # DESCRIPTION: 对换角标,例:参数 mv_to_tower1 tower3 可返回结果mv_to_tower3 tower1 # PARAMETERS: # RETURNS: #------------------------------------------------------------------------------- change_num () { way_num_tmp=` echo $1 |rev |cut -c1 ` change_from=` echo $2 |rev |cut -c1 ` way_output= ` echo "mv_to_tower"$change_from ` from_output=` echo "tower"$way_num_tmp level_up=(${level_up[*]} `echo "$way_output $from_output"` ) } # ---------- end of function change_num ---------- #--- FUNCTION ---------------------------------------------------------------- # NAME: tower_level_up # DESCRIPTION: 塔的移动方法随阶数的增加自动升级,并将其存入level_up() # PARAMETERS: # RETURNS: #------------------------------------------------------------------------------- tower_level_up () { #------------------------------------------------------------------------------- # 核心算法 汉诺塔学习升级 # 若是要求n阶汉诺塔:应先求3阶汉诺塔 # 经过三阶汉诺塔为基础进行变换 # 例:4阶汉诺塔的移动方法 # 3阶汉诺塔正向移动 + 第四阶移动到塔2 # +3阶汉诺塔反向移动 + 第四阶移动到塔3 # +3阶汉诺塔正向移动 # 由此可知若已有4阶汉诺塔的移动方法可求5阶移动方法 # 因此已知3阶汉诺塔可求n阶汉诺塔 # 但因为时间复杂度的提高和数据的溢出 # 不可求太高阶的汉诺塔 # #------------------------------------------------------------------------------- # 由于数组中存入了3阶汉诺塔的正向移动方法因此无需改变 for (( CNTR=3; CNTR<$1; CNTR+=1 )); do # 添加步骤 将高1阶的塔从塔1移动到塔2 level_up=(${level_up[*]} echo "mv_to_tower2 tower_1" # 防止计算错错误锁定低阶汉诺塔的正向移动方法的数组位置 arry_end=echo "`echo ${#level_up[@]}-2 |bc`" for (( i=0; i<$arry_end; i+=1 )); do # 生成反向移动,并存入数组 change_num ${level_up[$i]} done # 添加步骤 将高一阶的塔从塔2移动到塔3 level_up=(${level_up[*]} echo"mv_to_tower3 tower_2" # 再次使用低阶正向移动方法 for (( j=0; j<$arry_end; CNTR+=1 )); do level_up=(${level_up[*]} `echo ${level_up[j]}`) done done } # ---------- end of function tower_level_up ---------- main () {: # 输入一个要完成的阶数 # 生成数组 # create_tower # 传入tower_level_up # 得出目标方法 # 运行目标方法 # 输出countstep内容 # 便可得到移动步骤和最终塔 } # ---------- end of function main ----------