python用禁忌搜索算法实现TSP旅行商问题

使用python禁忌搜索算法实现TSP旅行商问题

计算智能课程作业,使用python实现禁忌搜索算法实现TSP旅行商问题
问题简介:
给定一系列城市和每对城市之间的距离,求解访问每一座城市一次并回到起始城市的最短回路。它是组合优化中的一个NP困难问题。

代码如下:

#!/usr/bin/python
#_*_ coding:utf-8 _*_  
import math
import random
import numpy as np 
import matplotlib.pyplot as plt
from mpl_toolkits.mplot3d import Axes3D
import sys
from numpy.matlib import rand
from matplotlib.mlab import dist
from matplotlib.artist import getp
import copy
from test.test__locale import candidate_locales
from cProfile import run


#初始三十个城市坐标
city_x = [41,37,54,25,7,2,68,71,54,83,64,18,22,83,91,25,24,58,71,74,87,18,13,82,62,58,45,41,44,4]
city_y = [94,84,67,62,64,99,58,44,62,69,60,54,60,46,38,38,42,69,71,78,76,40,40,7,32,35,21,26,35,50]
#城市数量
n = 30
distance = [[0 for col in range(n)] for raw in range(n)]

#禁忌表
tabu_list = []
tabu_time = []
#当前禁忌对象数量
current_tabu_num = 0
#禁忌长度,即禁忌期限
tabu_limit = 50
#候选集
candidate = [[0 for col in range(n)] for raw in range(200)]
candidate_distance = [0 for col in range(200)]
#最佳路径以及最佳距离
best_route = []
best_distance = sys.maxsize
current_route = []
current_distance = 0.0

def greedy():
    #通过贪婪算法确定初始r值,也就是初始信息素浓度       
    sum = 0.0
    #必须实例化一个一个赋值,不然只是把地址赋值,牵一发而动全身
    dis = [[0 for col in range(n)] for raw in range(n)]
    for i in range(n):
        for j in range(n):
            dis[i][j] = distance[i][j]
                
    visited = []
        #进行贪婪选择——每次都选择距离最近的
    id = 0
    for i in range(n):
        for j in range(n):
            dis[j][id] = sys.maxsize
        minvalue = min(dis[id])
        if i != 29:
            sum += minvalue
        visited.append(id)
        id = dis[id].index(minvalue)
    sum += distance[0][visited[n-1]]
    return visited


#构建初始参考距离矩阵
def getdistance():
    for i in range(n):
        for j in range(n):
            x = pow(city_x[i] - city_x[j], 2)
            y = pow(city_y[i] - city_y[j], 2)
            distance[i][j] = pow(x + y, 0.5)
    for i in range(n):
        for j in range(n):
            if distance[i][j] == 0:
                distance[i][j] = sys.maxsize
                
#计算总距离
def cacl_best(rou):
    sumdis = 0.0
    for i in range(n-1):
        sumdis += distance[rou[i]][rou[i+1]]
    sumdis += distance[rou[n-1]][rou[0]]     
    return sumdis

#初始设置
def setup():
    global best_route
    global best_distance
    global tabu_time
    global current_tabu_num
    global current_distance
    global current_route
    global tabu_list
    #得到初始解以及初始距离
    #current_route = random.sample(range(0, n), n) 
    current_route = greedy()
    best_route = copy.copy(current_route)
    #函数内部修改全局变量的值
    current_distance = cacl_best(current_route)
    best_distance = current_distance
    
    #置禁忌表为空
    tabu_list.clear()
    tabu_time.clear()
    current_tabu_num = 0

#交换数组两个元素
def exchange(index1, index2, arr):
    current_list = copy.copy(arr)
    current = current_list[index1]
    current_list[index1] = current_list[index2]
    current_list[index2] = current
    return current_list
    
    
#得到邻域 候选解
def get_candidate():
    global best_route
    global best_distance
    global current_tabu_num
    global current_distance
    global current_route
    global tabu_list
    #存储两个交换的位置
    exchange_position = []
    temp = 0
    #随机选取邻域
    while True:
        current = random.sample(range(0, n), 2)
        #print(current)
        if current not in exchange_position:
            exchange_position.append(current)
            candidate[temp] = exchange(current[0], current[1], current_route)
            if candidate[temp] not in tabu_list:
                candidate_distance[temp] = cacl_best(candidate[temp])
                temp += 1
            if temp >= 200:
                break
            
    
    #得到候选解中的最优解
    candidate_best = min(candidate_distance)
    best_index = candidate_distance.index(candidate_best)
    
    
    current_distance = candidate_best
    current_route = copy.copy(candidate[best_index])
    #与当前最优解进行比较 
    
    if current_distance < best_distance:
        best_distance = current_distance
        best_route = copy.copy(current_route)
    
    #加入禁忌表
    tabu_list.append(candidate[best_index])
    tabu_time.append(tabu_limit)
    current_tabu_num += 1    
    
#更新禁忌表以及禁忌期限
def update_tabu():
    global current_tabu_num
    global tabu_time
    global tabu_list
    
    del_num = 0
    temp = [0 for col in range(n)]
    #更新步长
    tabu_time = [x-1 for x in tabu_time]
    #如果达到期限,释放
    for i in range(current_tabu_num):
        if tabu_time[i] == 0:
            del_num += 1
            tabu_list[i] = temp
           
    current_tabu_num -= del_num        
    while 0 in tabu_time:
        tabu_time.remove(0)
    
    while temp in tabu_list:
        tabu_list.remove(temp)
    
    
    
def draw():
    result_x = [0 for col in range(n+1)]
    result_y = [0 for col in range(n+1)]
    
    for i in range(n):
        result_x[i] = city_x[best_route[i]]
        result_y[i] = city_y[best_route[i]]
    result_x[n] = result_x[0]
    result_y[n] = result_y[0]
    print(result_x)
    print(result_y)
    plt.xlim(0, 100)  # 限定横轴的范围
    plt.ylim(0, 100)  # 限定纵轴的范围
    plt.plot(result_x, result_y, marker='>', mec='r', mfc='w',label=u'Route')
    plt.legend()  # 让图例生效
    plt.margins(0)
    plt.subplots_adjust(bottom=0.15)
    plt.xlabel(u"x") #X轴标签
    plt.ylabel(u"y") #Y轴标签
    plt.title("TSP Solution") #标题
    
    plt.show()
    plt.close(0)  
    
                
def solve():
    getdistance()
    runtime = int(input("迭代次数:"))
    setup()
    for rt in range(runtime):

        get_candidate()
        update_tabu()
    
    print("当前距离:")
    print(current_distance)
    print(current_route)
    print("最优距离:")    
    print(best_route)
    print(best_distance)
    draw()    
    
if __name__=="__main__":
    solve()
    

实现效果
在这里插入图片描述

  • 4
    点赞
  • 64
    收藏
    觉得还不错? 一键收藏
  • 8
    评论
### 回答1: 遗传算法是一种基于生物进化原理的优化算法,可以用于求解TSP旅行商问题TSP问题是指在给定的一组城市和每对城市之间的距离下,找到一条经过每个城市一次且总距离最短的路径。 遗传算法的基本思想是将问题转化为一个个体的遗传过程,通过不断的交叉、变异和选择等操作,逐步优化种群中的个体,最终得到最优解。 具体实现过程如下: 1. 初始化种群:随机生成一定数量的个体,每个个体表示一条路径,即一组城市的访问顺序。 2. 评估适应度:计算每个个体的适应度,即路径长度。适应度越高,说明路径越短,个体越优秀。 3. 选择操作:根据适应度大小,选择一部分个体作为下一代的父代。 4. 交叉操作:对父代进行交叉操作,生成新的个体。交叉操作可以采用顺序交叉、部分映射交叉等方法。 5. 变异操作:对新生成的个体进行变异操作,引入一定的随机性。变异操作可以采用交换、插入、翻转等方法。 6. 评估适应度:计算新生成的个体的适应度。 7. 选择操作:根据适应度大小,选择一部分个体作为下一代的父代。 8. 重复步骤4-7,直到达到停止条件(如达到最大迭代次数、适应度达到一定阈值等)。 9. 输出最优解:从最终种群中选择适应度最高的个体作为最优解,即TSP问题的最短路径。 总之,遗传算法是一种有效的求解TSP问题的方法,可以通过不断的迭代优化,得到最优解。 ### 回答2: TSP问题指的是旅行商问题,即在一定的时间内,旅行商需要访问所有城市一次,最终回到起点,并且最小化行程距离。TSP问题作为优化问题,是计算机科学中的经典问题之一。传统的找到TSP问题最优解的求解方法是暴力枚举,但是对于较大的问题规模来说,这种方法变得非常不现实。因此,遗传算法成为了很好的解决方法。 遗传算法是一种优化算法,模拟自然界的进化过程,在解决问题时通过对“遗传信息”的编码进行选择、交叉、变异等操作从而达到全局最优或近似最优的解决方案。对于TSP问题,我们可以将遗传算法应用于其中,帮助我们找到全局最短路径。 具体实现时,我们将每个解看作一个种群中的个体,并对其进行随机编码,形成一个基因串。遗传算法会运用自然选择过程,筛选出适应度较高的基因串,构建适应度函数F。通过选择、交叉和种群变异操作,让基因串在不断迭代、进化的过程中,逐渐找到TSP的最优解。 具体实施步骤如下: 1. 确定优化目标和适应度函数:我们需要定义适当的算法来度量每个个体的适应度大小,例如,对于TSP问题,我们可以以旅行商需要走的总距离作为适应度函数,离初始点越近,所需距离越短,适应度就越高。 2. 生成种群:我们通过随机选择点来构建种群,每个种群中的个体表示不同的旅游路径。 3. 选择:通过在种群中选择一部分高适应度的个体,产生新的种群。 4. 交叉:在新的种群中选择一些个体进行交叉,重新生成新的种群。 5. 变异:在新的种群中选择一部分个体进行变异操作,即对某些基因序列进行随机修改,生成新的种群。 6. 迭代:重复3-5步,多次迭代后,选择适应度最高个体作为结果输出。 Python作为一种高阶编程语言,在处理遗传算法中的求解问题方面表现突出。在实现过程中,我们可以使用Python中的numpy模块来实现矩阵计算,使用matplotlib模块对结果进行可视化处理,并结合python的其它模块,如pandas、networkx等来进行数据处理和图形展示,最终得到一个完整的TSP问题求解。 ### 回答3: 旅行商问题TSP)是一个NP难问题,它假设有一位旅行商要访问n个城市,在每个城市之间都有一定的距离,要求旅行商走遍所有城市且回到起点的路径是最短的。遗传算法是一种解决TSP问题的有效方法之一,Python是一门流行的编程语言,能够方便地实现遗传算法。 遗传算法采用生物进化的概念,将问题的解表示为一个染色体,通过模拟基因交叉、变异等操作,逐代优化解的质量。在TSP问题中,每个染色体都表示一条路径。为方便操作,可以将每个路径用城市编号表示。 首先需要构建初始种群,方法可以采用随机生成、贪心算法等。每个染色体的适应度可以用路径长度来表示,路径长度越小,适应度越高。随后进行选择操作,选择适应度高的染色体进行繁殖。为获得更多的多样性,可以采用轮盘赌算法或锦标赛选择算法。 繁殖是遗传算法的重要过程之一,主要是模拟基因交叉和变异。基因交叉分为单点交叉、多点交叉、均匀交叉等方式,可以使用随机数生成器确定交叉点和交叉方式。变异是指染色体中的一些基因改变了其值,一般用于增加种群多样性。变异的方式包括随机突变、倒位变异等。 进行多代迭代后,可以得到最优解,其中最优解的染色体表示了旅行商走遍各个城市的最短路径。最后,将该染色体中编号转换为具体城市名称,即可得到最优路径。 总之,遗传算法是求解TSP问题的一种有效方法,Python语言具有简洁、高效和易于实现的特点,是实现遗传算法求解TSP问题的理想工具。
评论 8
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值