算法簡介
進退法的用途是爲一維極值優化問題尋找到一個包含極值的單峯區間,即從一點出發,試圖搜索到使函數呈現“高-低-高”的三點,從而得到一個近似的單峯區間。
算法適用問題
凸優化問題,即目標函數爲凸函數,若不是凸函數,則搜索到的單峯區間依賴初始值的選擇,一般只能找到包含極值的單峯區間,而找不到包含最值的區間,即只能搜索到局部最優,而非全局最優。
python實現
import matplotlib.pyplot as plt
plt.figure()
class advance_retreat_method(object):
"""
obj_func 爲需要尋找單峯區間的目標函數
x0爲給定的初始點
h0搜尋步長
"""
def __init__(self,obj_func,x0 = 0,h0 = 0.1):
self.h = h0
self.obj_func = obj_func
self.x1 = x0
self.x2 = x0 + h0
self.x3 = 0
self.y1 = 0
self.y2 = 0
self.y3 = 0
# 1、計算函數值
def func_value(self):
self.y1 = self.obj_func(self.x1)
self.y2 = self.obj_func(self.x2)
plt.plot([self.x1,self.x2],[self.y1,self.y2],marker = "*",color = "red",markersize = 15)
# 2、比較函數值大小
def compare_value(self):
if self.y1 < self.y2:
self.h = -self.h
a = self.x1
b = self.y1
self.x1 = self.x2
self.y1 = self.y2
self.x2 = a
self.y2 = b
else :
self.h = self.h
# 3、計算y3
def cal_y3(self):
self.x3 = self.x2+self.h
self.y3 = self.obj_func(self.x2+self.h)
plt.plot([self.x2,self.x3],[self.y2,self.y3],marker = "o",color = "blue")
# 4、比較y3與y2後判斷是否輸出單峯區間
def get_interval(self):
if self.y3 > self.y2:
if self.x1 < self.x3:
return [self.x1,self.x3]
else:
return [self.x3,self.x1]
else:
self.x1 = self.x2
self.y1 = self.y2
self.x2 = self.x3
self.y2 = self.y3
self.cal_y3()
return self.get_interval()
# 5、統籌運行
def run(self):
# 1、計算y1和y2
self.func_value()
# 2、比較函數值大小
self.compare_value()
# 3、計算y3
self.cal_y3()
# 4 比較y3與y2後判斷是否輸出單峯區間
result = self.get_interval()
return result
if __name__ == "__main__":
sample = lambda x:x**2
a = advance_retreat_method(sample,x0 = 0.5).run()
print(a)
示例運行結果
by CyrusMay 2020 04 28
曬傷的脫皮 意外的雪景
與你相依的四季
蒼狗又白雲 身旁有了你
匆匆輪迴又有何懼
——————五月天(如果我們不曾相遇)——————