离散免疫算法求解旅行商问题(源码实现)
生活随笔
收集整理的這篇文章主要介紹了
离散免疫算法求解旅行商问题(源码实现)
小編覺得挺不錯的,現(xiàn)在分享給大家,幫大家做個參考.
旅行商問題
????旅行商問題(TSP 問題)。假設(shè)有一個旅行商人要拜訪全國31個省會城市,他需要選擇所要走的路徑,路徑的限制是每個城市只能拜訪-一次, 而且最后要回到原來出發(fā)的城市。路徑的選擇要求是:所選路徑的路程為所有路徑之中的最小值。
免疫算法原理
???? 見鏈接:
萬字長文了解免疫算法原理 及求解復(fù)雜約束問題(源碼實現(xiàn))
二進制編碼
免疫算法(二進制)算例(源碼實現(xiàn))
MATLAB版求解
注意事項:由于旅行商問題中,各個個體不存在相同個體,所以無需計算濃度。
python版求解
import numpy as np import pandas as pd from tqdm import tqdm#進度條設(shè)置 import matplotlib.pyplot as plt from pylab import * import matplotlib; matplotlib.use('TkAgg') mpl.rcParams['font.sans-serif'] = ['SimHei'] mpl.rcParams['axes.unicode_minus'] = Falsecity_num = 31 # 城市的數(shù)量 #############1.數(shù)據(jù)集 城市坐標(biāo) C=[1304 ,2312,3639 ,1315,4177 ,2244,3712 ,1399,3488, 1535,3326, 1556,3238 ,1229,4196 ,1044,4312,790,4386,570,3007,1970,2562 ,1756,2788, 1491,2381 ,1676,1332,695,3715 ,1678,3918,2179,4061,2370,3780, 2212,3676, 2578,4029,2838,4263,2931,3429,1908,3507,2376,3394 ,2643,3439,3201,2935,3240,3140,3550,2545,2357,2778,2826,2370 ,2975] #31個省會城市坐標(biāo) C=np.array(C).reshape(-1,2)#shape=(31, 2)###############相關(guān)函數(shù):距離和親和度函數(shù)(路程) 路徑畫圖函數(shù)####################.函數(shù):計算城市之間的距離 def calculate_distance(X, Y):"""計算城市兩輛之間的歐式距離,結(jié)果用numpy矩陣存儲:param X: 城市的X坐標(biāo),np.array數(shù)組:param Y: 城市的Y坐標(biāo),np.array數(shù)組"""distance_matrix = np.zeros((city_num, city_num))for i in range(city_num):for j in range(city_num):if i == j:continuedis = np.sqrt((X[i] - X[j]) ** 2 + (Y[i] - Y[j]) ** 2) # 歐式距離計算distance_matrix[i][j] = disreturn distance_matrix##適應(yīng)度函數(shù) 計算總距離 def fitness_func(distance_matrix, xi):"""適應(yīng)度函數(shù),計算目標(biāo)函數(shù)值.:param distance: 城市的距離矩陣:param xi: PSO的一個解:return: 目標(biāo)函數(shù)值,即總距離"""total_distance = 0for i in range(1, city_num):start = xi[i - 1]end = xi[i]total_distance += distance_matrix[start][end]total_distance += distance_matrix[end][xi[0]] # 從最后一個城市回到出發(fā)城市return total_distance#路徑畫圖 def plot_tsp(gbest):"""繪制最優(yōu)解的圖形"""X=D[:,0]#城市坐標(biāo)的X軸Y=D[:,1]#城市坐標(biāo)的Y軸plt.scatter(X, Y, color='r')for i in range(1, city_num):start_x, start_y = X[gbest[i - 1]], Y[gbest[i - 1]]end_x, end_y = X[gbest[i]], Y[gbest[i]]plt.plot([start_x, end_x], [start_y, end_y], marker='>',alpha=0.8)start_x, start_y = X[gbest[0]], Y[gbest[0]]plt.plot([start_x, end_x], [start_y, end_y], color='b', alpha=0.8)plt.show()#############免疫算法相關(guān)函數(shù)############免疫操作函數(shù):克隆、變異、變異抑制 def variation(Sortf):"""param Sortf:按親和度大小排序后的群體return :af 經(jīng)過克隆、變異、變異抑制后的群體#變異原理:交換個體中兩個元素的位置"""Ncl = 10 # 克隆個數(shù)af = np.zeros((np.int(NP / 2), city_num),dtype=np.int) # 存儲變異后的個體for i in range(np.int(NP / 2)): # 遍歷前一半個體# 選激勵度前NP/2個體進行免疫操作a = Sortf[i] # 當(dāng)前個體 .shape(city_num,)a = a.reshape(-1, city_num) # (-1,維度city_num)Na = np.tile(a, (Ncl, 1)) # 對當(dāng)前個體進行克隆 Na.shape=(Ncl, city_num)for j in range(Ncl): # 遍歷每一個克隆樣本p1=np.random.randint(0,city_num,1)[0] # 隨機產(chǎn)生一個整數(shù)[0,31)p2 = np.random.randint(0, city_num, 1)[0] # [0,31)while p1 == p2:p1 = np.random.randint(0, city_num, 1)[0] # 隨機產(chǎn)生一個整數(shù)[0,31)p2 = np.random.randint(0, city_num, 1)[0] # [0,31)tmp = Na[j,p1]Na[j,p1] = Na[j,p2]Na[j,p2] = tmp# 保留克隆源個體Na[0, :] = Sortf[i]#####克隆抑制,保留親和度最高的個體NaMSLL = np.zeros((Ncl, 1)) # 存儲變異種群親和度值for j in range(Ncl): # 遍歷每一個克隆樣本NaMSLL[j] = fitness_func(D, xi=Na[j]) # 親和度=距離Index = np.argsort(NaMSLL, axis=0) # 激勵度按升序排序Index = Index[:, 0]NaSortf = Na[Index] # 排序后的種群af[i] = NaSortf[0] # 取最優(yōu)return af#免疫操作:創(chuàng)建新生種群 def refresh():bf = np.zeros((np.int(NP/2), city_num), dtype=np.int)for i in range(np.int(NP/2)): # 遍歷每一個個體bf[i, :] = np.random.choice(list(range(0, city_num)), size=city_num, replace=False) # 群體初始化return bf#############免疫算法開始############ D=calculate_distance(C[:,0], C[:,1])#任意兩個城市距離間隔矩陣 shape=(31, 31)NP=200 #免疫個體數(shù)目 G=600 #最大免疫代數(shù) f=np.zeros((NP,city_num),dtype=np.int) #用于存儲種群 shape=(200, 31) for i in range(NP):#遍歷每一個個體f[i,:]=np.random.choice(list(range(0, city_num)), size=city_num, replace=False)#群體初始化len=np.zeros((NP,1)) #存儲路徑長度 for i in range(NP):#遍歷每一個個體len[i]=fitness_func(D, xi=f[i]) #計算初始群體每個個體的路程長度###激勵度按升序排序 Index=np.argsort(len,axis=0) Index=Index[:,0] Sortf=f[Index] # #排序后的初始群體 shape=(200, 31)##############免疫循環(huán)############ trace=[] #記錄迭代激勵度最優(yōu)值 for gen in tqdm(range(G)):#遍歷每一次迭代af = variation(Sortf) # 選擇一半個體 進行克隆、變異、變異抑制 shape=(100, 31)aflen=np.zeros((af.shape[0],1)) #存儲af群體路徑長度 shape=(100, 1)for j in range(af.shape[0]):#遍歷af中的每一個個體aflen[j] = fitness_func(D, xi=af[j]) # 計算af群體每個個體的路程長度(親和度)bf = refresh() # 創(chuàng)建一半新生種群#bf.shape=(100, 31)bflen = np.zeros((bf.shape[0], 1)) # 存儲bf群體路徑長度 shape=(100, 1)for j in range(bf.shape[0]):#遍歷af中的每一個個體bflen[j] = fitness_func(D, xi=bf[j]) # 計算af群體每個個體的路程長度(親和度)# ##########種群刷新:免疫種群與新生種群合并##f1 = np.concatenate((af, bf), axis=0) # 合并的種群 f1.shape=(50, 2) f1為子代f1len = np.concatenate((aflen, bflen), axis=0) # 合并種群激勵度值 shape=(200, 1)Index = np.argsort(f1len, axis=0)Index = Index[:, 0]Sortf = f1[Index] # shape(50, 2)trace.append(fitness_func(D, xi=f1[0])) # 記錄最優(yōu)個體的激勵度值############輸出優(yōu)化結(jié)果 Bestf=Sortf[0,:] #最優(yōu)變量 print('最優(yōu)變量',Bestf) print('最優(yōu)值',trace[-1] ) #最優(yōu)值 plt.plot(trace) plt.title('迭代曲線') plt.show() plot_tsp(Bestf)作者:電氣 余登武
與50位技術(shù)專家面對面20年技術(shù)見證,附贈技術(shù)全景圖總結(jié)
以上是生活随笔為你收集整理的离散免疫算法求解旅行商问题(源码实现)的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 洁百利A7洗地机不出水怎么处理?
- 下一篇: 下沙到杭州人民医院怎么坐车方便?