-
-
程序源代码清单
1、窗体Pwny0的程序
Dim Ne(100, 100) As Integer ' 自然方阵
Dim c(100, 100) As Integer ' 幻方数组
Private m As Integer, r As Integer ' 幻方参数
Private ak As Integer, bk As Integer ' 方法、起点
Private v As Integer, w As Integer, s As Integer
Dim ckr As String, u As Integer, sk As Integer
Dim L(210) As Long ' 检验数组
Private n As Integer, a As Integer, b As Integer
Private z As Integer, k As Integer, t As Integer
Sub swcg(n) ' 通用幻方检验过程
Erase L
L(0) = n * (n * n + 1) / 2 ' 幻和
z = 2 * n + 2: k = 0
For i = 1 To n
For j = 1 To n
L(i) = L(i) + c(i, j)
' 验算幻方C的行和与列和
L(n + i) = L(n + i) + c(j, i)
Next j
Next i
For j = 1 To n
L(z - 1) = L(z - 1) + c(j, j)
L(z) = L(z) + c(n + 1 - j, j)
' 验算幻方C的两条对角线
Next j
For i = 1 To z ' 上述结果与幻方C的幻和比较
If L(i) <> L(0) Then k = k + 1
Next i
End Sub
Private Sub Command1_Click() ' 开始
Erase c, Ne ' 初始化数组
CK$ = " 要制作多少阶幻方?请输入大于七的自然数:"
nv$ = InputBox$(CK$, " 询问后单选")
n = Val(nv$)
a = n \ 2: b = a + 1 ' 设置重要参数
w = n Mod 4 ' 分出阶数n 所属类型
v = n + 1: m = n \ 4
sk = IIf(n < 31, 5, 6) ' 根据数位确定输出格式
t = 1
Picture2.Print
Picture2.Print " 排出 "; n; " 阶自然数阵Ne(i, j)如下: "
For i = 1 To n '
For j = 1 To n
Ne(i, j) = t
Picture2.Print Tab(sk * j); Ne(i, j);
t = t + 1
Next j
Picture2.Print
Next i
End Sub
Sub nycfym(n) ' 穿心对调主过程
Picture2.Print
If ak = 1 Then
Picture2.Print " 这是使用穿心对调二法:奇行换偶,偶行换奇"
ckr = " 穿心对调二法"
Else
Picture2.Print " 这是使用穿心对调一法:奇行换奇,偶行换偶"
ckr = " 穿心对调一法"
End If
For k = 1 To 2
bk = IIf(ak = 1, 3 - k, k) ' 奇行换奇,偶行换偶
For i = k To a Step 2
For j = bk To a Step 2 '
c(i, j) = Ne(v - i, v - j)
c(v - i, v - j) = Ne(i, j)
c(i, v - j) = Ne(v - i, j) ' 左右对称
c(v - i, j) = Ne(i, v - j) ' 穿心对调
Next j
Next i
Next k
End Sub
Sub oypb(n) ' 重排米字过程
If ak = 1 Then
For i = 1 To n ' 二法重排米字(顺向)
c(i, b) = Ne(i, v - i) ' 中列向下
c(i, v - i) = Ne(i, b) ' 副对角线向左下
c(b, i) = Ne(i, i) ' 中行向右
c(i, i) = Ne(b, i) ' 主对角线向右下
Next i
Else
For i = 0 To n - 1 ' 一法重排米字(逆向)
c(n - i, b) = n + (n - 1) * i ' 中列向上
c(b, n - i) = 1 + v * i ' 中行向左
c(n - i, 1 + i) = v / 2 + n * i ' 副对角线向右上
c(n - i, n - i) = (n - 1) * n / 2 + 1 + i
' 主对角线向左上
Next i
End If
End Sub
Private Sub Command6_Click() ' 对调中枢主程序
For i = 1 To n
For j = 1 To n
c(i, j) = Ne(i, j)
Next j
Next i
Call nycfym(n) ' 穿心对调主过程
If n Mod 2 = 0 Then ' 一、二法偶阶对调后调整
If w = 2 Then
For i = 2 To a - 1 ' 单偶阶上下对调a列
u = c(i, a): c(i, a) = c(v - i, a)
c(v - i, a) = u ' 再左右对调a+1行
u = c(b, i): c(b, i) = c(b, v - i)
c(b, v - i) = u
Next i
u = c(1, a): c(1, a) = c(1, b) '
c(1, b) = u ' 最后对调首行、首列的中间两项
u = c(a, 1): c(a, 1) = c(b, 1)
c(b, 1) = u
u = c(1, 3): c(1, 3) = c(n, 3)
c(n, 3) = u
u = c(3, 1): c(3, 1) = c(3, n)
c(3, n) = u
End If
ElseIf n Mod 2 = 1 Then ' 一、二法奇阶对调后调整
Call oypb(n) ' 加入十字,重排米字
If w = 3 Then
For i = 1 To a - 1 '4m+3 阶上下对调a列
u = c(a, i): c(a, i) = c(a, v - i)
c(a, v - i) = u
u = c(i, a): c(i, a) = c(v - i, a)
c(v - i, a) = u ' 再左右对调a行
Next i
u = c(a, a): c(a, a) = c(v - a, v - a)
c(v - a, v - a) = u ' 最后对调中心四项
u = c(a, b): c(a, b) = c(v - a, b)
c(v - a, b) = u
End If
End If
nk = IIf(n < 58, n, 57) ' 最多显示57列
For i = 1 To n ' 显示幻方
For j = 1 To nk
Picture2.Print Tab(sk * j); c(i, j);
Next j
Picture2.Print ' 换行
Next i
End Sub
Private Sub Command2_Click() ' 检验
swcg n ' 通用幻方检验过程
If k = 0 Then
Picture2.Print "C 是一个"; n, "阶幻方,其幻和为"; L(0), "它的每一行、每一列及两对角线上数之和都是:"; L(8)
MsgBox " 这个C是一个标准幻方。", 48, "检验结论:" ' 信息对话框
Else
Picture2.Print
Picture2.Print Tab(20); " 遗憾,C不是一个幻方!"; "其中有"; k; "条不符合要求。"
Exit Sub
End If
End Sub
Private Sub Command3_Click() ' 记录
Open "d:\09\ 穿心对调幻方A.txt" For Append As #1 '打开或创立文件
Print #1,
Print #1, " 使用 " & ckr & "制作的 "; n; " 阶幻方如下:"; "从1 填到 "; n * n
For i = 1 To n '50
For j = 1 To n
Print #1, Tab(sk * j); c(i, j);
Next j
Print #1,
Next i
If k = 0 Then
Print #1, "C 是一个"; n, "阶幻方,其幻和为"; L(0), _
" 它的每一行、每一列及两对角线上数之和都是:"; L(8)
Else
Print #1, Tab(20); " 遗憾,C不是一个幻方!"; "其中有"; k; "条不符合要求。"
End If
Print #1,
Close #1 ' 关闭这个文本
End Sub
Private Sub Command4_Click() ' 退出
End
End Sub
Private Sub Option1_Click(Index As Integer)
ak = Index ' 单选制作法
End Sub
Private Sub Command5_Click() ' 清屏
Picture2.Cls
HScroll1.Value = 10 ' 写入点返回左上角
VScroll1.Value = 10
End Sub
Private Sub Form_Load() ' 滚动图形窗口设置
Picture2.AutoSize = True
Picture1.BorderStyle = 0
Picture2.BorderStyle = 0
Picture2.Width = 31680
Picture2.Height = 31350
HScroll1.Max = Picture2.Width - Picture1.Width
VScroll1.Max = Picture2.Height - Picture1.Height
Option1(0).Value = True
End Sub
Private Sub HScroll1_Change() ' 水平滚动条变化
Picture2.Left = -HScroll1.Value
End Sub
Private Sub VScroll1_Change() ' 垂直滚动条变化
Picture2.Top = -VScroll1.Value
End Sub
-
程序运行与功能
-
- 8 阶自然数阵Ne及使用 穿心对调二法制作的 8 阶幻方如下:从1 填到 64
|
C是一个 8 阶幻方,其幻和为 260 它的每一行、每一列及两对角线上数之和都是: 260 |
1
|
2
|
3
|
4
|
5
|
6
|
7
|
8
|
9
|
10
|
11
|
12
|
13
|
14
|
15
|
16
|
17
|
18
|
19
|
20
|
21
|
22
|
23
|
24
|
25
|
26
|
27
|
28
|
29
|
30
|
31
|
32
|
33
|
34
|
35
|
36
|
37
|
38
|
39
|
40
|
41
|
42
|
43
|
44
|
45
|
46
|
47
|
48
|
49
|
50
|
51
|
52
|
53
|
54
|
55
|
56
|
57
|
58
|
59
|
60
|
61
|
62
|
63
|
64
|
|
1
|
63
|
3
|
61
|
60
|
6
|
58
|
8
|
56
|
10
|
54
|
12
|
13
|
51
|
15
|
49
|
17
|
47
|
19
|
45
|
44
|
22
|
42
|
24
|
40
|
26
|
38
|
28
|
29
|
35
|
31
|
33
|
32
|
34
|
30
|
36
|
37
|
27
|
39
|
25
|
41
|
23
|
43
|
21
|
20
|
46
|
18
|
48
|
16
|
50
|
14
|
52
|
53
|
11
|
55
|
9
|
57
|
7
|
59
|
5
|
4
|
62
|
2
|
64
|
|
-
图-2:自然方阵与穿心对调幻方
-
运行穿心对调幻方程序,出现主窗体界面。单击“开始”按钮,初始化幻方数组C与Ne,跳出输入对话框InputBox,在输入区内填入幻方阶数。幻方阶数n先限制在100以内,重新设置输出间隔sk后,阶数n可以继续向上;考虑到穿心对调是利用方阵的对称性,因而要求n≥8。确定后n阶自然数阵Ne显示在滚动窗口的图片框Picture2上。用单选按钮选定制作方法,单击“对调”按钮,调入中枢主过程nycfym(n)先予对调,再做后期调整形成幻方C,最后将这幻方C显示在滚动窗口的图片框Picture2上,供君观赏。单击“检验”按钮,则对所作幻方C进行幻和检验,在常规检验过程swcg(n)中,用循环语句For…Next将幻方C的每一行、每一列及两对角线的n个数累加起来,与幻和Sn=n(n2+1)/2相比较,均符合幻和则为标准幻方,以信息对话框MsgBox告知,并把结论显示在该幻方的下方。
-
当一幅图片快写完,垂直滚动条VScroll1的滑块到了最下方,这时单击“清屏”按钮,清除所显示的内容,光标(写入点)自动返回图片框的左上角。
-
图片框的宽度是有限的,本软件设置滚动显示幻方最多时是57列,再多的列将被略去。如要看全或之后仔细玩赏研究,可以单击“记录”按钮,程序将幻方及结论记录在事前创建的文件夹D\09中的穿心对调幻方A.txt文本内,图-2是一例,能再作打印或其它处理。
-
单击“退出”按钮后退出程序。此工程能生成可执行文件穿心对调幻方.exe,在windows95/98环境下使用,记住在硬盘D中先创建09文件夹以备记录。
-
-
穿心对调幻方的制作原理
-
以n阶方阵的行、列顺序依次排入自然数1 到n×n,得到的是n阶自然数阵Ne。见图-2左侧,在自然数阵里,关于中心对称的两项之和恒相等,为常数n2+1,称作两对称项;把关于中心(格)对称的两项互相调换位置,称为穿(中)心对调。
-
整除运算n\2=a, b=a+1是n阶方阵的重要参数,如n属于奇数,则Ne(b,b)是中行与中列相交的中心格;再由对称而言,我们只要穿心对调施行到a行a列即可。在穿心对调主过程nycfym(n)中,正是这样将n阶自然数阵Ne(i,j)中的数隔行、隔列交错对称地互换一半项,参阅图-2右侧,二法口诀是“奇行换偶,偶行换奇,左右对称,穿心对调”。
取模运算n mod 4用来求余数w,w将阶数分为四个类型,即双偶数4m、单偶数4m+2及奇数4m+1和4m+3。看样,穿心对调法最适合于4m阶,操作之后即得幻方;而对4m+2阶还要将中间多出的不平衡的两行、两列及一些项进行调整,这近似经验或灵感的调整,很难找出动作的规则,才是编程的艰难之处!参阅对调中枢主程序Private Sub Command6_Click()。对于奇数阶,施行穿心对调一法或二法后,得到的也不是幻方,必须将中行和中列及两对角线重新排列,称作重排米字,见oypb(n)过程及图-3例。4m+3阶最为复杂,还有调整部分项的第三步工作,才得幻方。VB编程时往往对不规范的另星动作熬尽脑汁,调试成功后才尝到胜利的喜悦,运行时转瞬间制得高阶幻方并加以验算,这才觉得电脑的效率与程序之伟大!
-
37
|
80
|
3
|
78
|
9
|
76
|
7
|
74
|
5
|
72
|
38
|
70
|
13
|
17
|
15
|
66
|
14
|
64
|
19
|
62
|
39
|
60
|
25
|
58
|
23
|
56
|
27
|
54
|
29
|
52
|
40
|
33
|
32
|
48
|
35
|
46
|
1
|
11
|
21
|
31
|
41
|
51
|
61
|
71
|
81
|
36
|
47
|
34
|
50
|
49
|
42
|
30
|
53
|
28
|
55
|
26
|
59
|
24
|
57
|
22
|
43
|
20
|
63
|
18
|
68
|
16
|
67
|
65
|
69
|
12
|
44
|
10
|
77
|
8
|
75
|
6
|
73
|
4
|
79
|
2
|
45
|
|
使用 穿心对调二法制作的 9 阶幻方如下:从1 填到 81
C是一个 9 阶幻方,其幻和为 369
图-3:9阶穿心对调幻方与米字示意
|
-
幻方制作是一个大课题,如果说马步法似奔驰疆场、军容严正,那么穿心对调法则是坐席论道、灵活机动。倘有机缘,以后再介绍其它制作法的 VB程序。读者若有兴趣可与我联系,电话:0712—2313763。
|