質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

新規登録して質問してみよう
ただいま回答率
85.50%
for

for文は、様々なプログラミング言語で使われている制御構造です。for文に定義している条件から外れるまで、for文内の命令文を繰り返し実行します。

if

if文とは様々なプログラミング言語で使用される制御構文の一種であり、条件によって処理の流れを制御します。

多次元配列

1次元配列内にさらに配列を格納している配列を、多次元配列と呼びます。

Python

Pythonは、コードの読みやすさが特徴的なプログラミング言語の1つです。 強い型付け、動的型付けに対応しており、後方互換性がないバージョン2系とバージョン3系が使用されています。 商用製品の開発にも無料で使用でき、OSだけでなく仮想環境にも対応。Unicodeによる文字列操作をサポートしているため、日本語処理も標準で可能です。

配列

配列は、各データの要素(値または変数)が連続的に並べられたデータ構造です。各配列は添え字(INDEX)で識別されています。

Q&A

2回答

1196閲覧

pythonの配列についてです

bbiiq

総合スコア51

for

for文は、様々なプログラミング言語で使われている制御構造です。for文に定義している条件から外れるまで、for文内の命令文を繰り返し実行します。

if

if文とは様々なプログラミング言語で使用される制御構文の一種であり、条件によって処理の流れを制御します。

多次元配列

1次元配列内にさらに配列を格納している配列を、多次元配列と呼びます。

Python

Pythonは、コードの読みやすさが特徴的なプログラミング言語の1つです。 強い型付け、動的型付けに対応しており、後方互換性がないバージョン2系とバージョン3系が使用されています。 商用製品の開発にも無料で使用でき、OSだけでなく仮想環境にも対応。Unicodeによる文字列操作をサポートしているため、日本語処理も標準で可能です。

配列

配列は、各データの要素(値または変数)が連続的に並べられたデータ構造です。各配列は添え字(INDEX)で識別されています。

0グッド

0クリップ

投稿2021/07/24 06:22

編集2022/01/12 10:55

トーナメントのようなものを実装したいのですが、for文の範囲がうまくいかず
list index out of range がスローされます。どこが悪いのでしょうか。
問題のコードとエラー、試したこと、全体のコードを記載します。

<問題のコード>

python

1#トーナメント選択 2def select(eva): 3 random.shuffle(eva) 4 tournament = [()] 5 while len(eva) > 1: 6 if len(eva) % 2 != 0: 7 for i in range(1,len(eva),1): 8 if eva[i] < eva[i+1]: 9 tournament.append(eva[i]) 10 else: 11 tournament.append(eva[i+1]) 12 eva = tournament 13 else: 14 for i in range(0,len(eva),1): 15 if eva[i] < eva[i+1]: 16 tournament.append(eva[i]) 17 else: 18 tournament.append(eva[i+1]) 19 eva = tournament 20 return tournament

エラー

python

1 38 else: 2 39 for i in range(0,len(eva),1): 3---> 40 if eva[i] < eva[i+1]: 4 41 tournament.append(eva[i]) 5 42 else: 6 7IndexError: list index out of range 8

<試したこと>
for i in range(0,len(tournament),1):
を、
for i in range(0,len(tournament)-1,1):
for i in range(0,len(tournament)-2,1):
for i in range(0,len(tournament),2):
など、終了条件を-1や-2にするなど、ステップを1から2にするなどしましたが同じエラーのままです。

<全体のコード>

python

1import random 2import copy 3 4random.seed(1870258) 5gene_length = 10 6# 遺伝子長 7individual_length = 10 # 個体数 8generation = 30 # 世代数 9 10#二次元配列で遺伝子長と個体数を表現 11def get_population(): 12 population = [] 13 for i in range(individual_length): #遺伝子長 14 population.append([random.randint(0,1) for j in range(gene_length)]) #個体数 15 return population 16 17#適応度 18def fitness(pop): 19 return sum(pop) 20 21#評価 22def evaluate(pop): 23 pop.sort(reverse=True) 24 return pop 25 26#トーナメント選択 27def select(eva): 28 random.shuffle(eva) 29 tournament = [()] 30 while len(eva) > 1: 31 if len(eva) % 2 != 0: 32 for i in range(1,len(eva),1): 33 if eva[i] < eva[i+1]: 34 tournament.append(eva[i]) 35 else: 36 tournament.append(eva[i+1]) 37 eva = tournament 38 else: 39 for i in range(0,len(eva),1): 40 if eva[i] < eva[i+1]: 41 tournament.append(eva[i]) 42 else: 43 tournament.append(eva[i+1]) 44 eva = tournament 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()

気になる質問をクリップする

クリップした質問は、後からいつでもMYページで確認できます。

またクリップした質問に回答があった際、通知やメールを受け取ることができます。

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

guest

回答2

0

if eva[i] < eva[i+1]: の行でエラーが出ているんだから、その直前に
print('len(eva) =', len(eva), 'i =', i) を入れて値を見てみよう
と思いませんか?

len(eva) が 10 で、i が 0~9 と変化すると、i+1 は 1~10 となり、
eva[i+1] が範囲外となるのは当然です。

デバッグとはそういうもんです。やってみませんか?

投稿2021/07/24 09:28

編集2021/07/24 12:21
kazuma-s

総合スコア8224

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

0

ループしながら、操作対象のリストの要素を削除しているからです。

削除すれば、リストが短かくなるので、いずれあったはずのインデックスのデータが存在しなくなります。

アルゴリズムを見直す必要がありまう。

投稿2021/07/24 06:49

TakaiY

総合スコア12666

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

bbiiq

2021/07/24 07:32 編集

回答ありがとうございます。 教えていただいたことを踏まえて変更してみましたが同じエラーのままです。どこが悪いのでしょうか。直接的な原因ではなくても、原因の調べ方などでも教えていただけると助かります。 コードをここに書きたかったのですがインデントがされないので質問自体を変更しました。
TakaiY

2021/07/24 10:27

ロジックを見ていませんが。 for i in range(0,len(eva),1): if eva[i] < eva[i+1]: このループのさせかたでは、ループの最後でevaの範囲を必ず越えてしまいます。
guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

まだベストアンサーが選ばれていません

会員登録して回答してみよう

アカウントをお持ちの方は

15分調べてもわからないことは
teratailで質問しよう!

ただいまの回答率
85.50%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問