トーナメントのようなアルゴリズムを実装したいのですが、リストやタプルの理解が浅くうまくいきません。
for文の範囲が間違っていると思うのですが、うまくいきません。
どうしたらよいのでしょうか。
<試したこと>
for i in range(0,len(tournament)-1,tour_num):
と変更したが同じエラーのままで、
for i in range(0,len(tournament)-2,tour_num):
としたところ、結果が表示されない。
<変数>
len(tournament) = 10
tour_num = 2
です。
python
1def select(eva): 2 tournament = [()] 3 tournament.append(random.shuffle(eva)) 4 while len(tournament) > 1: 5 if len(tournament) % 2 != 0: 6 for i in range(1,len(tournament),tour_num): 7 if tournament[i][0] < tournament[i+1][0]: 8 del tournament[i][0] 9 else: 10 del tournament[i+1][0] 11 else: 12 for i in range(0,len(tournament),tour_num): 13 if tournament[i][0] < tournament[i+1][0]: 14 del tournament[i][0] 15 else: 16 del tournament[i+1][0] 17 18 return tournament
エラー
38 else:
39 for i in range(0,len(tournament),tour_num):
---> 40 if tournament[i][0] < tournament[i+1][0]:
41 del tournament[i][0]
42 else:
IndexError: tuple index out of range
全体のコードも載せておきます。
python
1import random 2import copy 3 4random.seed(1870258) 5gene_length = 10 6# 遺伝子長 7individual_length = 10 # 個体数 8generation = 30 # 世代数 9tour_num = 2 #トーナメント数 10 11#二次元配列で遺伝子長と個体数を表現 12def get_population(): 13 population = [] 14 for i in range(individual_length): #遺伝子長 15 population.append([random.randint(0,1) for j in range(gene_length)]) #個体数 16 return population 17 18#適応度 19def fitness(pop): 20 return sum(pop) 21 22#評価 23def evaluate(pop): 24 pop.sort(reverse=True) 25 return pop 26 27#tトーナメント選択(次世代個体生成) 28def select(eva): 29 tournament = [()] 30 tournament.append(random.shuffle(eva)) 31 while len(tournament) > 1: 32 if len(tournament) % 2 != 0: 33 for i in range(1,len(tournament),tour_num): 34 if tournament[i][0] < tournament[i+1][0]: 35 del tournament[i][0] 36 else: 37 del tournament[i+1][0] 38 else: 39 for i in range(0,len(tournament),tour_num): 40 if tournament[i][0] < tournament[i+1][0]: 41 del tournament[i][0] 42 else: 43 del tournament[i+1][0] 44 45 return tournament 46 47 48#一点交叉 49def one_point_crossover(parent1, parent2): 50 r1 = random.randint(0, gene_length-1) 51 child1 = copy.deepcopy(parent1) 52 child2 = copy.deepcopy(parent2) 53 child1[r1:gene_length-1] = parent2[r1:gene_length-1] 54 child2[r1:gene_length-1] = parent1[r1:gene_length-1] 55 return child1,child2 56 57 58def main(): 59 # 初期個体生成 60 pop = evaluate([(fitness(p), p) for p in get_population()]) 61 print('Generation: 0') 62 print('Min : {}'.format(pop[-1][0])) 63 print('Max : {}'.format(pop[0][0])) 64 print('--------------------------') 65 66 for g in range(generation): 67 if 10 != pop[0][0] or 10 != pop[-1][0]: 68 69 g += 1 70 print('Generation: ' + str(g)) 71 72 73 eva = evaluate(pop) 74 tournament = select(eva) 75 pop = tournament 76 77 while len(pop) < individual_length: 78 m1 = random.randint(0, len(tournament)-1) 79 m2 = random.randint(0, len(tournament)-1) 80 child1,child2 = one_point_crossover(tournament[m1][1], tournament[m2][1]) 81 pop.append((fitness(child1), child1)) 82 pop.append((fitness(child2), child2)) 83 84 print('Min : {}'.format(pop[-1][0]),' Result : {}'.format(pop[-1])) 85 print('Max : {}'.format(pop[0][0]),' Result : {}'.format(pop[0])) 86 print('--------------------------') 87 else: 88 break 89 90 91 92 print('\n--------------------------End of evolution--------------------------') 93 print('Generation: ' + str(g)) 94 print('Min : {}'.format(pop[-1][0]),' Result : {}'.format(pop[-1])) 95 print('Max : {}'.format(pop[0][0]),' Result : {}'.format(pop[0])) 96 97 98 99if __name__ == '__main__': 100 main()
回答2件
あなたの回答
tips
プレビュー