今天给大家分享一下算法,用python来实现最优化算法。废话不多说,直接上代码:
一、二分法
函数详见rres,此代码使该算法运行了两次
def asdf(x): rres=8*x**3-2*x**2-7*x+3 return rresi=2left=0right=1while i>0 : i = i-1 ans = 0.1 mid1 = (left + right + ans) / 2 mid2 = (left + right - ans) / 2 a=asdf(mid1) c=asdf(mid2) if a > c : right = mid1 else : left = mid2b=(left+right) / 2print("左极限=%s,右极限=%s,极小值x=%s"%(left,right,b))
左极限=0.45,右极限=0.775,极小值x=0.6125
收获:
这是我第一个实现的代码。学习完该算法以后,逻辑框架基本上就有了,剩下需要明确的就是对应的python的语言。
于是我就开始了查找“如何定义函数”,“循环体”和“if条件语句”的格式(https://blog.csdn.net/qq_39407518/article/details/79822498)“数学符号”,以及print的使用。
1.def是python中指定义,一般用来定义函数,如果需要深度学习搭建网络可用来定义网络。值得注意的一点是
return必须要加在函数后面另起一行。
不太清楚为什么,但是如果没有加的话,那个函数公式就是一个花瓶,就像一个结果输不出去。
2.最坑的就是逻辑。一开始逻辑没理清楚,或者说在代码上有疏漏,导致我将left和right放在了循环体里,结果可想而知。不过也是因为这个错误,我知道pycharm中的debug怎么用,挺简单的,百度一下就出来了。
3.不知道什么原因,看的莫烦视频中的print多个变量一起输出是没有办法在我的pycharm中使用的,出来的结果很奇怪。可能是因为我是win10不是ios吧。print如果多个变量一起输出必须是print("名字:%s,名字2:%s"%(a,b))结果输出就是名字:a ,名字2:b
问题:1、为什么要加return?
return的意思是输出这个def里面任意一个变量值作为结果显示。一般情况而言,是输出函数的关系式的命名,这样当你调用这个函数的时候,变量对应的函数值才能显示出来,否则只运行没有结果,不会有效果。
二、格点法——三点等分法
import numpy as npdef qwer(x): third = np.exp(x) - 5*x return thirdleft = 1right = 2mid1 =float(left+right) / 2mid2 = (left+mid1) / 2mid3 = (mid1+right) /2a = qwer(mid1)b = qwer(mid2)c = qwer(mid3)i = 5while i > 0: i=i-1 if a > b: if c > b : #b right = mid1 mid1 = mid2 a=b mid2 = (left + mid1) / 2 mid3 = (mid1 + right) / 2 b = qwer(mid2) c = qwer(mid3) else:#b>c #c left = mid1 mid1 = mid3 a = c mid2 = (left + mid1) / 2 mid3 = (mid1 + right) / 2 b = qwer(mid2) c = qwer(mid3) else:#b>a if a > c: #C left = mid1 mid1 = mid3 a = c mid2 = (left + mid1) / 2 mid3 = (mid1 + right) / 2 b = qwer(mid2) c = qwer(mid3) else:#b>a&c>a # a left = mid2 right = mid3 mid2 = (left + mid1) / 2 mid3 = (mid1 + right) / 2 b = qwer(mid2) c = qwer(mid3)print("最小值=%s"%mid1)print("函数值=%s"%a)
最小值=1.609375函数值=-3.047189552275773
关于python中数据变量。第一遍运行结果出现很明显不对,于是我采用了debug。
结果发现,mid1处一直为1而不是1.5,于是就开始了解数据变量。起初我猜测python默认所有变量为整型,但是根据二分法的结果我意识到此猜测不对,所以要改整个file的变量格式没有必要。
所以我就在mid1式子前面加了一个float,结果就显示为1.5了。但是如果我将整个式子用()括起来,前面加float,结果还是1。我不太理解为什么。
不过我知道了python的数据格式是根据输入量决定的,也就是说你的输入量如果是整型,那么与其直接相关的计算输出结果一定是整型,而且还是不采用进位的整型。
在我没有采用+float/+.0这两种方法之前,mid1~3全部是整型。
left = 1.0right = 2.0mid1 =(left+right) / 2
或者不再mid1前面加float,直接将输入量后面点个点就行。
三、Fibonacci法
def fibonacci(n): i=0 a = 0 b = 1 for i in range(n): i=i+1 c = a+b a = b b = c return cdef bn(x): ert = x**2 - 6*x + 2 return ertz = 2p = 0left = 0.00000right = 10.00000L1 = right - leftwhile z < 100: m = fibonacci(z) l = L1/m k = 1.000/m if k < 0.03: print("n=%s,Fn=%s"%(z,m)) L2 = l*fibonacci(z-1) t = left + L2 r = right -L2 while p < 3: p = p + 1 l3 = t - r e= bn(t) o = bn(r) if e>o : right = t t = r r = left + l3 else:#o>e left = r r = t t = right - l3 break else: z = z + 1okk=(left+right)/2okky=bn(okk)print(left)print(right)print("极小值x=",okk)print("极小值y=",okky)
四、黄金分割法
def gold(x): gg= x**2 - 6*x + 9 return ggleft = 1right = 7ans = 0.4a = left + 0.618 * (right - left)b = left + 0.382*(right - left)gga = gold(a)ggb = gold(b)i = 0while i < 7: print("i=%s" % i) print("left=%s,right=%s" % (left, right)) print("x左=%s,x右=%s" % (a, b)) print("y左=%s,y右=%s" % (ggb, gga)) c = right - left if c > 0.4: i = i + 1 if gga > ggb: right = a a = b b = left + 0.382*(right - left) gga = ggb ggb = gold(b) else:#gga
五、间接法——二次插值法
def yy(x): y=x**4-4*x**3-6*x**2-16*x+4 return ydef xing(xm1,xm2,xm3,fm1,fm2,fm3): yxxx=0.5000*((xm2**2-xm3**2)*fm1+(xm3**2-xm1**2)*fm2+(xm1**2-xm2**2)*fm3)/((xm2-xm3)*fm1+(xm3-xm1)*fm2+(xm1-xm2)*fm3) return yxxxx1 = -1.0000f1 = yy(x1)x3 = 6f3 = yy(x3)x2 = 0.50000*(x1+x3)f2 = yy(x2)xp = xing(x1,x2,x3,f1,f2,f3)fp = yy(xp)a = abs(xp-x2)while abs(xp-x2) > 0.05000: a = abs(xp - x2) if xp > x2: if fp > f2: x3=xp f3=fp xp = xing(x1, x2, x3, f1, f2, f3) fp = yy(xp) print("ans=%s" % a) print("left=%s,right=%s" % (x1, x3)) print("x*=%s,fp*=%s" % (xp, fp)) print("x2=%s,f2=%s" % (x2, f2)) print("******************") else:#f2>fp x1 = x2 f1 = f2 x2 = xp f2 = fp xp = xing(x1, x2, x3, f1, f2, f3) fp = yy(xp) print("ans=%s" % a) print("left=%s,right=%s" % (x1, x3)) print("x*=%s,fp*=%s" % (xp, fp)) print("x2=%s,f2=%s" % (x2, f2)) print("******************") else:#xp f2: x1 = xp f1 = fp xp = xing(x1, x2, x3, f1, f2, f3) fp = yy(xp) print("ans=%s" % a) print("left=%s,right=%s" % (x1, x3)) print("x*=%s,fp*=%s" % (xp, fp)) print("x2=%s,f2=%s" % (x2, f2)) print("******************") else: x3 = x2 f3 = f2 x2 = xp f2 = fp xp = xing(x1, x2, x3, f1, f2, f3) fp = yy(xp) print("ans=%s" % a) print("left=%s,right=%s" % (x1, x3)) print("x*=%s,fp*=%s" % (xp, fp)) print("x2=%s,f2=%s" % (x2, f2)) print("******************")
六、间接法——牛顿法
def fd(x): y = 4*x**3-12*x**2-12*x-16 return ydef fdd(x): ys = 12*x**2-24*x-12 return ysi = 1x0 = 3.00000ans = 0.001while i < 7: fd0 = fd(x0) fdd0 = fdd(x0) if abs(fd0) > ans: x1 = x0 - (fd0/fdd0) x0 = x1 print("次数:%s,所得的值x:%s"%(i,x1)) i = i + 1 else:#fd0<0.001 print("$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$") print("Bingo!顺利通关!祝您开学愉快!") print("Boss X=%s"%x0) break
一开始while里面,导致run不出来。继而,debug也没法用。
后来在网上一查才知道 “没联网”+“没选断点”。最后想尝试将else里面的内容输出来,结果发现run以后被刷屏了。于是改成i<7以后还是不行,于是想着加一个break跳出循环,结果成效了。
然后刚刚由debug了一下,才知道原来是i+1在if里面,因为没有办法+1,所以i=6一直存在,就不断循环。因为加break也好,i+1也好,都可以。
如若需要python相关学习资料:例如“人工智能”、“爬虫”、“数据库”、“web开发”等类似学习参考资料书籍。关注小编,私信即可。
1、如何获取
2、关注小编
私信小编:回复 Python 即可领取资料
头条怎么私信
点击头条,点击右下角“我的”
在个人界面点击关注,如果你关注了,点击“小杆货”就可以了
私信回复:python就可以了 但是你要先关注我哦~