汉诺塔
Posted yant07
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了汉诺塔相关的知识,希望对你有一定的参考价值。
昨天户外拓展的时候,教练安排了“汉诺塔”这个游戏,目的是考验大伙的智力和团队合作能力。
当汉诺塔的层数增加的时候,明显觉得排列组合的难度大了很多。其实,如果换一种思维去想这个问题,就会觉得其实不那么难。
可以把整个汉诺塔看成两个部分,最底端的套圈(A)和除去最底端的套圈之外的其他套圈(B)。 那目标就变得简单了:
1. 将B挪开(移动到缓冲区)
2. 移动A到目标区
3. 将缓冲区的B移动到A上
举个例子,当只有2个套圈时,只需要移动B,再移动A,再将B移动到A上,一共3步即可完成。当有3个套圈的时候,我们把B当成一个整体,先挪开,再组合,挪开和组合就是移动这个整体(2个套圈)两次,中间再加一步移动A,所以理论上最少需要(3*2+1=7)步。同理,4个套圈需要(7*2+1)15步。可以通过归纳法得到步数为2n-1。
可以把这种思想用递归来表示出来,那就是:
def move(n,from1,buffer,to): global k if n==1: print (from1 ,‘->‘, to) k=k+1 print (k) else: move(n-1, from1, to, buffer) move(1, from1, buffer, to) move(n-1, buffer, from1, to) k=0 move(4,"a","b","c") print("%d steps in total."%k) a -> b 1 a -> c 2 b -> c 3 a -> b 4 c -> a 5 c -> b 6 a -> b 7 a -> c 8 b -> c 9 b -> a 10 c -> a 11 b -> c 12 a -> b 13 a -> c 14 b -> c 15 15 steps in total.
P.S. : a b c分别是三根柱子
OK,既然到了这里。可否多想一步?尝试train一个model,让model能够知道汉诺塔的下一步该如何移动。
思路如下:以n=4为例,汉诺塔完成移动一共最少需要15步。可以把汉诺塔抽象成15*3*4的三维资料库,每一笔资料看成一个有序的二维数组(3*4)。
移动的方式可以抽象成6种:
a -> b 1 a -> c 2 b -> c 3 c -> a 4 c -> b 5 b -> a 6
最后用Keras搭建LSTM框架。
import os
import pandas as pd import numpy as np os.chdir(r"C:\\Users\\yant07\\Desktop\\han") han=pd.read_csv("han.csv",header=None) dataX=han.loc[:,0:2] X1=np.array(dataX) X=np.reshape(X1,(15,3,1)) y=han.loc[:,3] y=pd.get_dummies(y) from keras.layers.core import Activation, Dense #from keras.layers import Embedding,Masking from keras.layers.recurrent import LSTM from keras.models import Sequential from keras.preprocessing import sequence #from sklearn.model_selection import train_test_split model = Sequential() model.add(LSTM(32, input_shape=(X.shape[1], X.shape[2]))) model.add(Dense(y.shape[1], activation=‘softmax‘)) model.compile(loss=‘categorical_crossentropy‘, optimizer=‘adam‘, metrics=[‘accuracy‘]) model.fit(X, y, nb_epoch=5000, batch_size=1, verbose=1) 15/15 [==============================] - 0s 4ms/step - loss: 0.7316 - acc: 0.7333 Epoch 212/5000 15/15 [==============================] - 0s 4ms/step - loss: 0.7247 - acc: 0.8000 Epoch 213/5000 15/15 [==============================] - 0s 4ms/step - loss: 0.7211 - acc: 0.8000 Epoch 214/5000 15/15 [==============================] - 0s 4ms/step - loss: 0.7122 - acc: 0.8000 Epoch 215/5000 15/15 [==============================] - 0s 4ms/step - loss: 0.7145 - acc: 0.8000 Epoch 216/5000 15/15 [==============================] - 0s 4ms/step - loss: 0.7052 - acc: 0.8667 Epoch 217/5000 15/15 [==============================] - 0s 4ms/step - loss: 0.7011 - acc: 0.8667 Epoch 218/5000 15/15 [==============================] - 0s 4ms/step - loss: 0.6948 - acc: 0.8667 Epoch 219/5000 15/15 [==============================] - 0s 5ms/step - loss: 0.6868 - acc: 0.8667 ...
发现准确率并不是很高。86% 主要原因可能是抽象出来的数据结构并没有完全区分所有情况,也可能是数据量有限。
最后祝大家周末愉快~ :p
以上是关于汉诺塔的主要内容,如果未能解决你的问题,请参考以下文章