机房因英语口语考试,按政策要求要到6月底才能启用。我校现阶段的信息技术需到教室上课,找一些适合在教室讲授的信息技术学科知识,仍是我主要面对的问题。
信息技术的深入应用促进了多个学科的发展,多个学科的教科书上可直接看到信息技术应用的内容,特别是在数学的教科书上。例如2019新人教版高中数学必修一的“用计算机绘制函数图像”、“用二分法求方程的近似解”等。
本文将从程序设计的角度,谈谈二分法求方程的近似解。
高中数学必修一是学生上一个学期已学习的内容,在讲授二分法求方程的近似解的程序之前,需回顾以往知识。
一、问题的提出
在十六世纪,人们已找到了三次和四次函数的求根公式,曾经希望得到一般的五次以上代数方程的根式解,但经过长期的努力仍无结果。1824年,挪威年轻数学家阿贝尔(N.
H. Abel,1802-1829)成功地证明了五次以上一般方程没有根式解。1828年,法国天才数学家伽罗瓦(E.Galois,1811-1832)巧妙而简洁地证明了存在不能用开方运算求解的具体方程。
虽然指数方程、对数方程和5次以上的高次代数方程等,不能用代数运算求解,但其数值解法却随着现代计算技术的发展得到了广泛的运用,我们可以用二分法等数值解法求方程的近似解。
二、课本例题回顾
以上表格数据与函数图像我利用了Excel的自动填充、函数运算、图表工具快速设计,让学生感受到了信息技术应用的便捷。
问题1:根据函数零点存在定理,可以知道函数f(x)=lnx+2x-6在区间(2,3)内存在一个零点,如何求出这个零点?你能求其精确值吗?
问题2:当精确度为0.01时,你能得到一个符合要求的零点的近似值吗?
取区间(2,3)的中点2.5,Excel算得f(2.5)=-0.084,因为f(2.5)f(3)<0,所以零点在区间(2.5,3)内。再取区间(2.5,3)的中点2.75,Excel算得f(2.75)≈0.512。因为f(2.5)f(2.75)<0,所以零点在区间(2.5,2.75)内,重复这样的步骤继续缩小零点所在区间,直到区间长度小于0.01为止。
当精确度为0.01时,因为|2.5390625-2.53125|<0.01,所以区间(2.53125,2.5390625)内任意一点都可以作为函数f(x)=lnx+2x-6零点的近似值,也即方程lnx+2x-6=0的近似解。
问题3:根据求函数f(x)=lnx+2x-6零点的近似值的过程,你能提炼出给定精确度ε,用二分法求函数y=f(x)零点x0的近似值的一般步骤吗?
教科书上给出“二分法”的定义及求解函数零点的一般步骤。如下。
注:这里前面的内容都为相关的数学知识回顾,后面的内容则对问题从编程的角度展开了具体分析,并进行编程测试。
追问:上面一般步骤第3步第3点条件f(c)*f(b)<0需不需要做判断?
该问题的提出主要是为后面的程序流程图做铺垫,流程图中只做了前2点条件的判断,并没有判断f(c)*f(b)是否小于0。这里从求解问题的步骤描述与流程图稍为不同,所以需要进一步理清该问题:为何可以不判断第3点条件f(c)*f(b)<0?
我在黑板上绘制如下图形。提出c点位置在区间[a,b]中相对于零点位置,只存在3种可能。(1)c点在零点之上。(2)c点在零点的右侧。(3)c点在零点的左侧。
(1)当c点在零点之上时,f(c)=0,这对应于一般步骤第3步第1点条件。
(2)当c点在零点的右侧时,又因a点在零点的左侧,f(a)、f(c)的值正负相反,故而f(a)*f(c)<0,这对应于一般步骤第3步第2点条件。
(3)排除掉前面两种可能,c点必定在零点的左侧,也就是对应于一般步骤第3步第3点条件。
在分析过程中,我与学生又同时回顾了根据c点的不同位置,零点所在区间的收缩变化。
三、编程求方程的近似解
问题4:你能根据上述的一般步骤画出程序流程图吗?
我向学生指出,流程图中的条件判断后3种情况与上文分析的3种情况一一对应。使学生了解程序流程图的绘制必须在问题分析的基础之上。
问题5:请用一种程序设计语言进行编程,完成以下练习。
限于教室的教学条件,我使用Excel自带的编程工具Visual Basic,向学生讲解求方程x=3-lgx的近似解的具体过程。
代码如下:
'方程 x=3-lg(x) 的近似解
Sub binary ()
Dim
a As Single, b As Single, k As Single, y As Single, x As Single
Dim
fa As Single, fb As Single, fc As Single
a
= 2
x
= a
fa
= 3 - (Log(x) / Log(10)) - x
b
= 3
x
= b
fb
= 3 - (Log(x) / Log(10)) - x
k
= 0.01
Do
While (Abs(a - b) > k)
c
= (a + b) / 2
x
= c
fc
= 3 - (Log(x) / Log(10)) - x
If
fa * fc < 0 Then
b
= c
Else
If
fc = 0 Then
a
= c
Exit
Do
Else
a
= c
End
If
End
If
Loop
MsgBox
"方程 x=3-lg(x) 的近似解为"
& a
End Sub
运行该程序,不用1秒即可得到方程的近似解。对于其它复杂方程的求解,只要改变初始区间a、b的值,及函数的表达式,运行程序后也可立即得到相应的近似解。
二分法通过不断缩小函数零点所在区间求方程的近似解,体现出用函数观点处理数学问题的思想和逐渐逼近的极限思想。本节通过回顾学生已学习的数学知识,再讲授求方程的近似解的程序,使学生巩固了相关数学知识的同时,了解程序设计的一般过程。对比繁复、耗时的手工取值运算求近似解的过程,他们直接感受到了计算机自动化执行指令的效率!而对于程序代码的分析,也有助于提升学生的计算思维。
此外,我再进一步介绍计算机科学中的二分法:二分查找算法。
四、拓展,二分查找
在程序设计中,当需要从大量数据进行查找时,就可应用二分法查找,但是数据需要先排好顺序。二分查找的主要思想是:(1)将被查找的数组array[low,
high]排序;(2)取数组区间 [low,
high]的中间位置K;(3)将查找的值T与元素array[k]比较,若相等,查找成功返回此位置;否则确定新的查找区域,继续二分查找。
应用二分查找,每一次查找与中间值比较,可以确定是否查找成功,不成功当前查找区间将缩小一半,从而提高了查找的效率。
二分查找的范例Python代码如下:
mylist =
[20,50,22,-22,0,15,222,28,29,99,1999,100823,55,35,5,1,2,3,8,9,55,10239,234234]
def
lgfind(arr,v):
arr
= sorted(arr)#排序数组,从小到大
print(arr)
start
= 0 #变量开始
arrLen
= len(arr)-1 #变量结束
while(
start <= arrLen
):
mid
= (start + arrLen) // 2 #变量中间值
print('mid',mid)
#如果中间的找到直接返回
if
arr[mid] == v:
return
v
#比对大小,看看我们要的结果是在上半段,还是下半段
if
arr[mid] > v:
arrLen=
mid - 1 #结果在上半段
else:
start=
mid + 1 #结果在下半段
return
false #没有则返回假
have = lgfind(mylist,222)
print(have)
运行结果:
通过运行结果可以发现,程序将数据排序,仅经过了4次取中间值后便查找到相应的数据。
参考资料: