自己想出来的~~~~~和网络上的算法基本一致~~~~~~~
Dim d(2) As Integer
Dim x As Integer
Private Sub Command1_Click()
x = 0
If Not Label1.UBound = 1 Then
For i = 2 To Label1.UBound '卸载多余的Label
Unload Label1(i)
Next
End If
For i = 2 To Val(Text1.Text) '加载需要的Label
Load Label1(i)
Label1(i).Width = 135 + 120 * i '赋予合适宽度
Next
For i = 1 To Label1.UBound '赋予合适位置
Label1(i).Left = Line1(1).X1 - Label1(i).Width \ 2
Label1(i).Top = Line1(1).Y2 - 255 * (Label1.UBound - i + 1)
Label1(i).Visible = True
Next
d(1) = Label1.UBound: d(2) = 0: d(0) = 0 '三根杆定义为1,2,0;初始化杆上的盘子数
Timer1.Enabled = True
End Sub
Private Function DMove(Disk As Integer, DFrom As Integer, DTo As Integer) '画盘子移动的代码
Label1(Disk).Top = Line1(DTo).Y2 - 255 * (d(DTo) + 1)
Label1(Disk).Left = Line1(DTo).X1 - Label1(Disk).Width \ 2
d(DFrom) = d(DFrom) - 1: d(DTo) = d(DTo) + 1 '盘子数的改变
End Function
Private Function KMove(Num As Integer, Disks As Integer, Disk As Integer, Temp As Integer) As Integer '移动过程的核心代码
For k = 1 To Disks
If (Num And 2 ^ k - 1) = 2 ^ (k - 1) Then '判断当前步数化为二进制后,最后一个不是0的字
KMove = (((Num \ 2 ^ k + 1) Mod 3) * (((Disks - k) Mod 2) * 2 - 1) + 4) Mod 3
'判断这个盘子在哪根杆上。因为每次移动盘只有两种顺序:
'1-2-0-1-2……或0-2-1-0-2-1……所以很容易判断
Temp = (KMove - (((Disks - k) Mod 2) * 2 - 1) + 3) Mod 3 '确定应该移动到哪里
Disk = k
Exit For
End If
Next
End Function
Private Sub Timer1_Timer()
Dim dd As Integer, t As Integer, kt As Integer
x = x + 1 '移动次数加1
If x = 2 ^ Label1.UBound Then '结束了:n个盘子需要2^n次移动
Timer1.Enabled = False
Exit Sub
End If
t = KMove(x, Label1.UBound, dd, kt) '移动盘子
DMove dd, kt, t '画盘子
End Sub
Dim d(2) As Integer
Dim x As Integer
Private Sub Command1_Click()
x = 0
If Not Label1.UBound = 1 Then
For i = 2 To Label1.UBound '卸载多余的Label
Unload Label1(i)
Next
End If
For i = 2 To Val(Text1.Text) '加载需要的Label
Load Label1(i)
Label1(i).Width = 135 + 120 * i '赋予合适宽度
Next
For i = 1 To Label1.UBound '赋予合适位置
Label1(i).Left = Line1(1).X1 - Label1(i).Width \ 2
Label1(i).Top = Line1(1).Y2 - 255 * (Label1.UBound - i + 1)
Label1(i).Visible = True
Next
d(1) = Label1.UBound: d(2) = 0: d(0) = 0 '三根杆定义为1,2,0;初始化杆上的盘子数
Timer1.Enabled = True
End Sub
Private Function DMove(Disk As Integer, DFrom As Integer, DTo As Integer) '画盘子移动的代码
Label1(Disk).Top = Line1(DTo).Y2 - 255 * (d(DTo) + 1)
Label1(Disk).Left = Line1(DTo).X1 - Label1(Disk).Width \ 2
d(DFrom) = d(DFrom) - 1: d(DTo) = d(DTo) + 1 '盘子数的改变
End Function
Private Function KMove(Num As Integer, Disks As Integer, Disk As Integer, Temp As Integer) As Integer '移动过程的核心代码
For k = 1 To Disks
If (Num And 2 ^ k - 1) = 2 ^ (k - 1) Then '判断当前步数化为二进制后,最后一个不是0的字
KMove = (((Num \ 2 ^ k + 1) Mod 3) * (((Disks - k) Mod 2) * 2 - 1) + 4) Mod 3
'判断这个盘子在哪根杆上。因为每次移动盘只有两种顺序:
'1-2-0-1-2……或0-2-1-0-2-1……所以很容易判断
Temp = (KMove - (((Disks - k) Mod 2) * 2 - 1) + 3) Mod 3 '确定应该移动到哪里
Disk = k
Exit For
End If
Next
End Function
Private Sub Timer1_Timer()
Dim dd As Integer, t As Integer, kt As Integer
x = x + 1 '移动次数加1
If x = 2 ^ Label1.UBound Then '结束了:n个盘子需要2^n次移动
Timer1.Enabled = False
Exit Sub
End If
t = KMove(x, Label1.UBound, dd, kt) '移动盘子
DMove dd, kt, t '画盘子
End Sub