Technology sharing

Python34 Algorithmus Genetic (GA)

2024-07-12

한어Русский языкEnglishFrançaisIndonesianSanskrit日本語DeutschPortuguêsΕλληνικάespañolItalianoSuomalainenLatina

1. Progressus historiae

Algorithmus geneticus (GA) est optimization algorithmus inspiratus ab electione naturali et genetica. Propositum est primum ab Americano scholari John Holland in annis 1970, studium adaptabilitatis in systematibus naturalibus intendens et ad problemata optimizatione in scientia computatrali applicata.

Clavis progressionis historiae
  • 1975Iohannes Holland primus conceptum algorithmi genetici in libro "Accommodationis in Systematibus Naturalibus et Artificialibus" proposuit.

  • 1980s: Algorithmae geneticae in campis adhiberi coeperunt ut optimizationem et optimam compositionem functionem ac sensim attentionem attraherent.

  • 1990s: Cum emendatione computandi vim computandi, algorithmi genetici late usi sunt in machinatione, oeconomica, biologia et aliis agris.

  • 2000s ad praesentem: Theoria et applicatione algorithm geneticorum longius progressi sunt, et varietas algorithmorum emendatorum ortae sunt, uti.遗传编程Geneticae Programming)、差分进化Evolutionis differentialis etc.

2. Mathematica principia

Algorithmus geneticus est methodus quaerendi temere secundum electionem et geneticam naturalem. Eius idea fundamentalis est processus evolutionis biologici simulare.eligeretransireetMutationesOperatio, novam incolarum generationem continenter generant, ita paulatim ad optimam solutionem accedunt.

Gradus fundamentales algorithmus geneticae
  1. initialization ": Passim generant initialem multitudinem.

  2. eligere: Elige melius singulos ex idoneitate functionis.

  3. transire: Novam partem permutando singula genes parentis singula.

  4. Mutationes: Passim quaedam gene individui.

  5. Iterate: Reitera lectio, crossover, et processus mutationis usque ad conditionem terminationem occurrit.

mathematica descriptionem

Pone magnitudinem incolarum N et chromosomatum uniuscuiusque longitudinis esse L. Processus mathematicus algorithmi genetici sic est:

  1. initialization ": Plebs generale, ubi chromosomatum est.

  2. Calculum idoneitatem: Aestimare idoneitatem quantitatis uniuscuiusque hominis.

  3. eligere: selectae personae secundum idoneitatem valorum.

  4. transire: Select aliquos homines ad operationem transversalem ad generandos novos homines.

  5. Mutationes: Mutationes operationes in quibusdam novis individuis ad generandum mutatur individua.

  6. population update: veteres homines repone cum novis hominibus ad novam hominum generationem formandam.

  7. Terminatio conditio: Si conditio praesentis terminationis (ut numerus iterations vel limen congruentiae) ventum est, optima solutio est output.

3. Application missionibus

Algorithmi genetici late in multis agris usi sunt propter aptam et robustam;

Ipsum ipsum
  • Optimization structuralis: Consilium leve et summae vi structurae.

  • Parameter optimization: Parametris adaequare systema bene agendi.

Oeconomica et Finance
  • Portfolio Optimization: collocare investment bona ad maximize redit.

  • forum praedictio: Predicts stock prices and market trends.

bioinformatics
  • Gen: Confer et DNA sequentia resolve.

  • Dapibus structura praedictio: Praedicunt tres dimensiones dapibus.

apparatus doctrina
  • Neural network disciplina: Optimize pondera et structura retiacula neural.

  • Pluma lectio: Elige notas quae maxime utiles sunt ad classificationem seu regressionem.

4. Visual exsecutio Pythonis exempla

picturam

Exemplum sequentis codicis algorithmum geneticum instruit ad problema venditoris iter solvendum.旅行商问题(TSP) problema est optimiizationis classicae combinatorialis quae intendit invenire viam brevissimam pro venditore peregrino ut unamquamque urbem visitaret in certo urbium statuto semel exacte ac tandem redire ad urbem incipiens, hoc est ad totam peregrinationem distantiam vel extenuandum. Sumptus, late usus in logisticis, schedulingis et aliis agris productio.

Primum definimus omnes urbes provinciales in Sina capitalia (includingTaipeium, caput provinciae Taiwan Sinarum) ac data coordinata et usu哈夫曼公式Distantiam duorum punctorum et pass遗传算法Populum initialem crea, generationem sequentem effingere, immutare et generare, iter continue optimize, ac denique notare distantiam et debitam viam brevissimae in unaquaque generatione, viam brevissimam in omnibus iterationibus invenire, eamque visibiliter in charta monstrare.Omnes urbis locisOpportunitas mutat numerum iterations Ut via optimal, ultimus eventus ostendit viam brevissimam a Chongqing per omnes civitates et totam eius distantiam. In summa duarum disciplinarum factae sunt. Primus numerus iteratio 2000 erat et tempus currit circiter 3 minuta.

Ad summam in una sententia: incipiens a Chongqing, iter ad omnes civitates capitales provincias in Sinis, et algorithmos geneticae uti ad brevissimam viam inveniendam. Sequens est signum exsecutionis:

  1. import numpy as np
  2. import matplotlib.pyplot as plt
  3. from mpl_toolkits.basemap import Basemap
  4. import random
  5. from math import radians, sin, cos, sqrt, atan2
  6. # 设置随机种子以保证结果可重复
  7. random.seed(42)
  8. np.random.seed(42)
  9. # 定义城市和坐标列表,包括台北
  10. cities = {
  11.     "北京": (39.9042116.4074),
  12.     "天津": (39.3434117.3616),
  13.     "石家庄": (38.0428114.5149),
  14.     "太原": (37.8706112.5489),
  15.     "呼和浩特": (40.8426111.7511),
  16.     "沈阳": (41.8057123.4315),
  17.     "长春": (43.8171125.3235),
  18.     "哈尔滨": (45.8038126.5349),
  19.     "上海": (31.2304121.4737),
  20.     "南京": (32.0603118.7969),
  21.     "杭州": (30.2741120.1551),
  22.     "合肥": (31.8206117.2272),
  23.     "福州": (26.0745119.2965),
  24.     "南昌": (28.6820115.8579),
  25.     "济南": (36.6512117.1201),
  26.     "郑州": (34.7466113.6254),
  27.     "武汉": (30.5928114.3055),
  28.     "长沙": (28.2282112.9388),
  29.     "广州": (23.1291113.2644),
  30.     "南宁": (22.8170108.3665),
  31.     "海口": (20.0174110.3492),
  32.     "重庆": (29.5638106.5507),
  33.     "成都": (30.5728104.0668),
  34.     "贵阳": (26.6477106.6302),
  35.     "昆明": (25.0460102.7097),
  36.     "拉萨": (29.652091.1721),
  37.     "西安": (34.3416108.9398),
  38.     "兰州": (36.0611103.8343),
  39.     "西宁": (36.6171101.7782),
  40.     "银川": (38.4872106.2309),
  41.     "乌鲁木齐": (43.825687.6168),
  42.     "台北": (25.032969121.565418)
  43. }
  44. # 城市列表和坐标
  45. city_names = list(cities.keys())
  46. locations = np.array(list(cities.values()))
  47. chongqing_index = city_names.index("重庆")
  48. # 使用哈夫曼公式计算两点间的距离
  49. def haversine(lat1, lon1, lat2, lon2):
  50.     R = 6371.0  # 地球半径,单位为公里
  51.     dlat = radians(lat2 - lat1)
  52.     dlon = radians(lon1 - lon2)
  53.     a = sin(dlat / 2)**2 + cos(radians(lat1)) * cos(radians(lat2)) * sin(dlon / 2)**2
  54.     c = 2 * atan2(sqrt(a), sqrt(1 - a))
  55.     distance = R * c
  56.     return distance
  57. # 计算路径总距离的函数,单位为公里
  58. def calculate_distance(path):
  59.     return sum(haversine(locations[path[i]][0], locations[path[i]][1], locations[path[i + 1]][0], locations[path[i + 1]][1]) for i in range(len(path) - 1))
  60. # 创建初始种群
  61. def create_initial_population(size, num_cities):
  62.     population = []
  63.     for _ in range(size):
  64.         individual = random.sample(range(num_cities), num_cities)
  65.         # 确保重庆为起点
  66.         individual.remove(chongqing_index)
  67.         individual.insert(0, chongqing_index)
  68.         population.append(individual)
  69.     return population
  70. # 对种群进行排名
  71. def rank_population(population):
  72.     # 按照路径总距离对种群进行排序
  73.     return sorted([(i, calculate_distance(individual)) for i, individual in enumerate(population)], key=lambda x: x[1])
  74. # 选择交配池
  75. def select_mating_pool(population, ranked_pop, elite_size):
  76.     # 选择排名前elite_size的个体作为交配池
  77.     return [population[ranked_pop[i][0]] for i in range(elite_size)]
  78. # 繁殖新个体
  79. def breed(parent1, parent2):
  80.     # 繁殖两个父母生成新个体
  81.     geneA = int(random.random() * (len(parent1) - 1)) + 1
  82.     geneB = int(random.random() * (len(parent1) - 1)) + 1
  83.     start_gene = min(geneA, geneB)
  84.     end_gene = max(geneA, geneB)
  85.     child = parent1[:start_gene] + parent2[start_gene:end_gene] + parent1[end_gene:]
  86.     child = list(dict.fromkeys(child))
  87.     missing = set(range(len(parent1))) - set(child)
  88.     for m in missing:
  89.         child.append(m)
  90.     # 确保重庆为起点
  91.     child.remove(chongqing_index)
  92.     child.insert(0, chongqing_index)
  93.     return child
  94. # 突变个体
  95. def mutate(individual, mutation_rate):
  96.     for swapped in range(1, len(individual) - 1):
  97.         if random.random() < mutation_rate:
  98.             swap_with = int(random.random() * (len(individual) - 1)) + 1
  99.             individual[swapped], individual[swap_with= individual[swap_with], individual[swapped]
  100.     return individual
  101. # 生成下一代
  102. def next_generation(current_gen, elite_size, mutation_rate):
  103.     ranked_pop = rank_population(current_gen)
  104.     mating_pool = select_mating_pool(current_gen, ranked_pop, elite_size)
  105.     children = []
  106.     length = len(mating_pool) - elite_size
  107.     pool = random.sample(mating_pool, len(mating_pool))
  108.     for i in range(elite_size):
  109.         children.append(mating_pool[i])
  110.     for i in range(length):
  111.         child = breed(pool[i], pool[len(mating_pool)-i-1])
  112.         children.append(child)
  113.     next_gen = [mutate(ind, mutation_rate) for ind in children]
  114.     return next_gen
  115. # 遗传算法主函数
  116. def genetic_algorithm(population, pop_size, elite_size, mutation_rate, generations):
  117.     pop = create_initial_population(pop_size, len(population))
  118.     progress = [(0, rank_population(pop)[0][1], pop[0])]  # 记录每代的最短距离和代数
  119.     for i in range(generations):
  120.         pop = next_generation(pop, elite_size, mutation_rate)
  121.         best_route_index = rank_population(pop)[0][0]
  122.         best_distance = rank_population(pop)[0][1]
  123.         progress.append((i + 1, best_distance, pop[best_route_index]))
  124.     best_route_index = rank_population(pop)[0][0]
  125.     best_route = pop[best_route_index]
  126.     return best_route, progress
  127. # 调整参数
  128. pop_size = 500       # 增加种群大小
  129. elite_size = 100     # 增加精英比例
  130. mutation_rate = 0.005 # 降低突变率
  131. generations = 20000   # 增加迭代次数
  132. # 运行遗传算法
  133. best_route, progress = genetic_algorithm(city_names, pop_size, elite_size, mutation_rate, generations)
  134. # 找到最短距离及其对应的代数
  135. min_distance = min(progress, key=lambda x: x[1])
  136. best_generation = min_distance[0]
  137. best_distance = min_distance[1]
  138. # 图1:地图上显示城市位置
  139. fig1, ax1 = plt.subplots(figsize=(1010))
  140. m1 = Basemap(projection='merc', llcrnrlat=18, urcrnrlat=50, llcrnrlon=80, urcrnrlon=135, resolution='l', ax=ax1)
  141. m1.drawcoastlines()
  142. m1.drawcountries()
  143. m1.fillcontinents(color='lightgray', lake_color='aqua')
  144. m1.drawmapboundary(fill_color='aqua')
  145. for i, (lat, lon) in enumerate(locations):
  146.     x, y = m1(lon, lat)
  147.     m1.plot(x, y, 'bo')
  148.     ax1.text(x, y, str(i), fontsize=8)
  149. ax1.set_title('City Locations')
  150. plt.show()
  151. # 图2:适应度随迭代次数变化
  152. fig2, ax2 = plt.subplots(figsize=(105))
  153. ax2.plot([x[1for x in progress])
  154. ax2.set_ylabel('Distance (km)')
  155. ax2.set_xlabel('Generation')
  156. ax2.set_title('Fitness over Iterations')
  157. # 在图中标注最短距离和对应代数
  158. ax2.annotate(f'Gen: {best_generation}nDist: {best_distance:.2f} km'
  159.              xy=(best_generation, best_distance), 
  160.              xytext=(best_generation, best_distance + 100),
  161.              arrowprops=dict(facecolor='red', shrink=0.05))
  162. plt.show()
  163. # 图3:显示最优路径
  164. fig3, ax3 = plt.subplots(figsize=(1010))
  165. m2 = Basemap(projection='merc', llcrnrlat=18, urcrnrlat=50, llcrnrlon=80, urcrnrlon=135, resolution='l', ax=ax3)
  166. m2.drawcoastlines()
  167. m2.drawcountries()
  168. m2.fillcontinents(color='lightgray', lake_color='aqua')
  169. m2.drawmapboundary(fill_color='aqua')
  170. # 绘制最优路径和有向箭头
  171. for i in range(len(best_route) - 1):
  172.     x1, y1 = m2(locations[best_route[i]][1], locations[best_route[i]][0])
  173.     x2, y2 = m2(locations[best_route[i + 1]][1], locations[best_route[i + 1]][0])
  174.     m2.plot([x1, x2], [y1, y2], color='g', linewidth=1, marker='o')
  175. # 只添加一个代表方向的箭头
  176. mid_index = len(best_route) // 2
  177. mid_x1, mid_y1 = m2(locations[best_route[mid_index]][1], locations[best_route[mid_index]][0])
  178. mid_x2, mid_y2 = m2(locations[best_route[mid_index + 1]][1], locations[best_route[mid_index + 1]][0])
  179. ax3.annotate('', xy=(mid_x2, mid_y2), xytext=(mid_x1, mid_y1), arrowprops=dict(facecolor='blue', shrink=0.05))
  180. # 在最优路径图上绘制城市位置
  181. for i, (lat, lon) in enumerate(locations):
  182.     x, y = m2(lon, lat)
  183.     m2.plot(x, y, 'bo')
  184.     ax3.text(x, y, str(i), fontsize=8)
  185. # 添加起点和终点标记
  186. start_x, start_y = m2(locations[best_route[0]][1], locations[best_route[0]][0])
  187. end_x, end_y = m2(locations[best_route[-1]][1], locations[best_route[-1]][0])
  188. ax3.plot(start_x, start_y, marker='^', color='red', markersize=15, label='Start (Chongqing)')  # 起点
  189. ax3.plot(end_x, end_y, marker='*', color='blue', markersize=15, label='End')   # 终点
  190. # 添加总距离的图例
  191. ax3.legend(title=f'Total Distance: {best_distance:.2f} km')
  192. ax3.set_title('Optimal Path')
  193. plt.show()

Locus visualisationis omnium civitatum capitalium provinciarum in Sinis:

picturam

Numerus iterationum est 2,000 (brevissima distantia est 31594 chiliometrorum);

Invenire iterationem brevissimam in processu iterationis historico et brevissimam viam visualize.

picturam

picturam

Causa II: numerus iterations est 20000 (brevissimum spatium adeptus est 29,768 chiliometrorum)

Iterationem cum brevissima via in iteratione historica reperies et brevissimam illam iterationem visualize.

picturam

picturam

Superius contentum ex interreti recapitulatum est. Si utile est, deinceps te vide.