陈维龙
摘要:VB是常用的程序设计语言,简捷、易用,运行稳定,运行效率较高。在数学教学中,常遇到一些逻辑复杂,个例较多,难于归纳总结的问题,教师在准备与讲析这些问题的时候很难找到解决思路,无所适从。笔者将这些问题通过VB编译成程序来运行处理,可以充分发挥计算机的优势,迅速解决这些数学难题。
关键词:VB;穷举法;数学问题
● 问题提出
前几天,上小学四年级的儿子指着试卷上的一个填空题,问我怎么做,题目描述:“用4、5、6、7、8这五个数组成一个两位数和一个三位数,乘积最大是( ),乘积最小是( )”。初一看好像是很简单的一道题,我和妻子两个人想当然地找出了多个组合,可马上都被自己的新发现打破,百思不得其解。于是,又上网搜索相关问题,得出各类答案与解决方案,但都有一些缺陷,有些规则看似有用,但当把题中的五个数字更换为其他数时,规则又不一定适用。其间,我们虽然已找到了最大值和最小值,但却不知道是不是恰当的答案。于是,我想到设计一个程序,用程序来解决这个问题,并试图在此基础上找到解答此类问题的规则。
● 算法分析
此类问题,在找不出明显的规则之前,只有通过穷举法罗列出符合要求的全部组合,计算出每个组合的最大值与最小值,将每个组合的组合规则记录到规则数组中,当穷举完所有的组合后,整理规则数组,去除重复的值,也就是组合规则,然后可以找出最大值组合与最小值组合的规律。因为此类题很少出现0这个数,所以我设计时只用了1~9这九个数,总结出来的规律可适用于有0出现求最大乘积的情况,求最小乘积的情况要稍作变通。描述算法如下:
①本程序通过嵌套循环,从1~9这九个数中选取随机五个不重复的数,作为题干中要求的五个个位数,并列出所有可能出现的组成一个两位数和一个三位数的组合。
②在①循环中,每次找到符合要求的五个个位数后,将其分别填入五个文本框中,并均作如下运算,先采用冒泡法,对这五个数进行从小到大排序,并依次填回五个文本框中。然后对用于存放乘数、乘积及数值组合规则的四个数组进行重定义,以便能够存储新得到的六个数及两个数值组合规则。然后对刚取得的五个个位数进行操作,通过嵌套循环,分别将任意两个或三个组成一个数,再将剩下的三个数或两个数组成另一个数,连同所得到的两个乘积及数值组合规则一起存入数组。当这五个个位数的所有可能组合均运算成功并存入相应数组后,从乘积数组中找出最大值和最小值,以及与之相对应的两组乘数和数值组合规则,输出到富文本框RB1,同时将数值组合规则写入最大值规则与最小值规则数组str_gzb()中。
③判断①循环是否符合循环要求,如果符合,再进入下一次循环。如果已完成所有符合要求的组合的运算,则退出循环。
④去除规则数组str_gzb()中重复项,统计出最大值和最小值的组合规则。也可以将得要的结果拷贝到Excel中,手工统计组合规则。
⑤数值组合规则规定如下:五个数字中最小的数所处的位置用A表示,最大的数所处的位置用E表示,其他类推。如题干中的4、5、6、7、8五个数,组成一个两位数47,其取值规则就是AD,组成一个三位数568,其取值规则就是BCE,在取值规则数组中记录为“ADBCE”。
● VB程序设计过程
在有了比较完善的算法分析之后,我利用VB程序进行了设计。过程为:
①在VB中建立一个工程,增加一个窗体form1。
②在窗体中添加数组控件text1(0~4)、command1、Richtextbox1等控件,并设置command1控件的Caption属性为“开始计算!”,设置Richtextbox1控件的名称为“RB1”,调整各控件到适当位置。
③添加窗体load代码,声明所要用到的各个动态数组,在command1中添加运算过程代码,添加用于记录所选取数值组合规则的过程GL的代码。
④运算测试,修缮程序。
⑤将工程输出为可执行文件。
● 源码
利用VB程序设计完成后,所有的源代码也一一完成,清晰地展现了利用此程序进行数学运用、算法分析的过程。部分源代码如下。
Private Sub Form_Load()
Dim S() As Integer '存放乘积
Dim G(), H() As Integer '存放乘数一 ,乘数二
Dim Str_Gz() As String '存放当前算术表述式规则
Dim str_gzb() As String '存放所有数据组合中最大值和最小值规则数组
Dim Str_bs As String '保存当前算术表述式的变量
Dim Str_Gz1, Str_Gz2 As String '存放本次循环最大值和最小值的数值组合规则
End Sub
Private Sub Command1_Click()
Dim Ta, Tb, Tc, Td, Te As Integer '存放五个随机的个位数的变量
Dim nIndex As Long '循环变量
Dim A, B, C, D, E, F As Integer '循环变量
ReDim str_gzb(2)
RB1.Text = RB1.Text & "所选数字 Max算式 Max规则 Max乘积Min算式 Min规则 Min乘积" & vbCrLf '设置列表的简易列头
For Ta = 1 To 9
For Tb = 1 To 9
For Tc = 1 To 9
For Td = 1 To 9
For Te = 1 To 9
If Ta <> Tb And Ta <> Tc And Ta <> Td And Ta <> Te And Tb <> Tc And Tb <> Td And Tb <> Te And Tc <> Td And Tc <> Te And Td <> Te Then
Text1(0).Text = Ta
Text1(1).Text = Tb
Text1(2).Text = Tc
Text1(3).Text = Td
Text1(4).Text = Te
……
ReDim Preserve str_gzb(UBound(str_gzb()) + 2) '不作判断直接重定义这个数组,会增加一些空值,但不影响对数值组合规则的统计
str_gzb(UBound(str_gzb()) - 1) = Str_Gz1
str_gzb(UBound(str_gzb())) = Str_Gz2
……
RB1.Text = RB1.Text & "******************************************" & vbCrLf
RB1.Text = RB1.Text & "乘积最大的组合规则和乘积最小的组合规则:" & vbCrLf
For i = 0 To UBound(str_gzb) '此循环部分代码借鉴网络代码,去除最值组合规则数组中重复项
For j = 0 To i – 1
If str_gzb(i) = str_gzb(j) Then Exit For
Next
If j = i Then RB1.Text = RB1.Text & str_gzb(i) & vbCrLf
Next
End Sub
……
Else
If N(i) = A Then GL = GL & "A" "A"表示此位置是五个数中最小的数,其余类推
If N(i) = B Then GL = GL & "B"
If N(i) = C Then GL = GL & "C"
If N(i) = D Then GL = GL & "D"
If N(i) = E Then GL = GL & "E"
End If
Next i
End Function
● 运行测试
设计完此程序后,我进行了测试,因为运算量大,程序运行时间一般需要一个小时以上,程序也可能出现假死现象,只要耐心等待即可。运行结果如下图(图片根据运行结果进行了拼接)。
由分析结果可以看出,此类问题的组合规则如下:将最大数作为两位数的十位,第四大数作为两位数的个位,将第二大数作为三位数的百位,第三大数作为三位数的十位,最小数作为三位数的个位,这样组合出来的两位数和三位数乘积最大;将最小数作为两位数的十位,第三大数作为两位数的个位,将第四大数作为三位数的百位,第二大数作为三位数的十位,最大数作为三位数的个位,这样组合出来的两位数和三位数乘积最小。
● 思考
作为一款经典的高级程序设计语言,VB的生命力依然旺盛,依然可以作为中小型程序的首选语言。