13

これを行うには、より良い方法が必要です。私はプログラミングは初めてですが、これは非常に非効率的な方法であり、これには関数が必要であることを知っています。正確に行う方法がわかりません。助言がありますか?どんな助けにもとても感謝しています!

for H in range(0,len(a_list)):
    if a_list[H] > list4[0]:
        list5 = [number_list[i]]
        if function(list1,list5) == list1[1]:
            if function(list2,list5)== list2[1]:
                if function(list3,list5)== list3[1]:
                    if function(list4,list5)== list4[1]:
                        list5.append(input('some input from the user'))
                        other_function(list5)
                        if list5[1]== 40:
                            print ('something something')
                            break out of EVERY loop 
                         else: 
                            for H in range(0,len(a_list)):
                                if a_list[H] > list5[0]:
                                    list6 = [number_list[i]]
                                    if function(list1,list6) == list1[1]:
                                        if function(list2,list6)== list2[1]:
                                            if function(list3,list6)== list3[1]:
                                               if function(list4,list6)== list4[1]:
                                                  if function(list5,list6)== list5[1]:
                                                     list6.append(input('some input from theuser'))
                                                     other_function(list6)
                                                         if list6[1]== 40:
                                                             print ('something something')
                                                                 break out of EVERY loop 
                                                         else: 
                                                            etc. (one extra comparison every time)  
4

2 に答える 2

13

all()関数を使用して、関連する複数の条件をテストします。

if all(function(lst, list5) == lst[1] for lst in (list1, list2, list3, list4)):

if all(function(lst, list6) == lst[1] for lst in (list1, list2, list3, list4, list5)):

ネストされたifステートメントと同様に、all()短絡します。Falseいずれかのテストが失敗するとすぐに戻ります。

さらに、インデックスの範囲を生成する代わりに、リストを直接ループします。を使用している場合は、別のレベルのインデントを削除して、どちらもbreak使用する必要はありません。else

フィルタリングして別のレベルを削除できますa_list

for H in filter(lambda H: H > list4[0], a_list):

一緒に、これによりネストが次のように減少します。

for H in filter(lambda H: H > list4[0], a_list):
    list5 = [number_list[i]]
    if all(function(lst, list5) == lst[1] for lst in (list1, list2, list3, list4)):
        list5.append(input('some input from the user'))
        other_function(list5)
        if list5[1]== 40:
            print ('something something')
            break # out of EVERY loop 

        for J in filter(lambda J: J >list5[0], a_list):
            if all(function(lst, list6) == lst[1] for lst in (list1, list2, list3, list4, list5)):
            list6.append(input('some input from theuser'))
            other_function(list6)
            if list6[1]== 40:
                print ('something something')
                break # out of EVERY loop 

            # continue here

通常のステートメントは現在のループを停止するだけなので、おそらくbreakステートメントは実際に例外 ( raise CustomException()and try:, except CustomException: # break out of all the loops fast) を使用します。break

リストとネストを継続的に追加している場合は、リストを使用してネストされたすべてのリストを保持し、外側のリストに単純に追加することをお勧めします。

class EndLoops(Exception): pass

stack = [[number_list[0]]]
try:
    for i in number_list[1:]:
        for H in filter(lambda H: H > stack[-1][0], a_list):
            stack.append([i])
            if all(function(lst, stack[-1]) == lst[1] for lst in stack[:-1]):
                stack[-1].append(input('some input from the user'))
                other_function(stack[-1])
                if stack[-1][1] == 40:
                    print ('something something')
                    raise EndLoops
except EndLoops:
    pass # broken out of outer loop

そして突然、入れ子がすべてなくなりました。代わりに、ネストをstackリストのリストに移動しました。

私はあなたのコードで最も外側のループがどのように見えるか分からないことに注意してください.

于 2013-12-05T13:29:13.470 に答える
5

番号が付けられ、同様に使用される変数が 3 つ以上ある場合は、リストを考えてください。

それを念頭に置いて、最初に list1、list2、list3、... をリストのリストに変更します (インデックスは 1,2,3,4 ではなく 0,1,2,3 です)。listただし、それはすでに有用なものの有用な名前であるため、呼び出さないでください。lstはPythonでかなり人気があります。また、list5 を lstA に、list6 を lstB に変更します。これは、5 と 6 が意味をなさないためです。

これで次のようになりました。

for H in range(0,len(a_list)):
    if a_list[H] > lst[3][0]:
        lstA = [number_list[i]]
        if function(lst[0],lstA) == lst[0][1]:
            if function(lst[1],lstA)== lst[1][1]:
                if function(lst[2],lstA)== lst[2][1]:
                    if function(lst[3],lstA)== lst[3][1]:
                        lstA.append(input('some input from the user'))
                        other_function(lstA)
                        if lstA[1]== 40:
                            print ('something something')
                            break out of EVERY loop 
                         else: 
                            for H in range(0,len(a_list)):
                                if a_list[H] > lstA[0]:
                                    lstB = [number_list[i]]
                                    if function(lst[0],lstB) == lst[0][1]:
                                        if function(lst[1],lstB)== lst[1][1]:
                                            if function(lst[2],lstB)== lst[2][1]:
                                               if function(lst[3],lstB)== lst[3][1]:
                                                  if function(lstA,lstB)== lstA[1]:
                                                     lstB.append(input('some input from theuser'))
                                                     other_function(lstB)
                                                         if lstB[1]== 40:
                                                             print ('something something')
                                                                 break out of EVERY loop 
                                                         else: 
                                                            etc. (one extra comparison every time)  

これで、基本的に同じことを 4 回行っていることがより明確になりました。


同じことを何度も行う必要がある場合は、ループを考えてください。

ブロックをループに変更します。また、フラグ変数を使用して、ロジックのテスト中に何かが失敗したかどうかを追跡し、「機能する場合は何かを実行する」ではなく、「機能しない場合はスキップする」ロジックを使用します。

for H in range(0,len(a_list)):
    if a_list[H] > lst[3][0]:
        continue #reducing indent levels by negating the check:
                 #quit on failure instead of work on success

    lstA = [number_list[i]]

    quit = False

    for j in range(4):
        if function(lst[j],lstA) != lst[j][1]: #testing FALSEHOOD
            quit = True
            break #the j loop only

    if quit:
        continue #reducing indent levels by negating the check

    lstA.append(input('some input from the user'))
    other_function(lstA)
    if lstA[1]== 40:
        print ('something something')
        break #out of EVERY loop
    #else: #don't need the else because we broke

    for H in range(0,len(a_list)):
        if not a_list[H] > lstA[0]:
            continue #reducing indent levels by negating the check

        lstB = [number_list[i]]

        for j in range(4):
            if function(lst[j],lstB) != lst[j][1]: #testing FALSEHOOD
                quit = True;
                break #to the H loop
        if not quit and  function(lstA,lstB)== lstA[1]: #combining two checks
            lstB.append(input('some input from theuser'))
            other_function(lstB)
            if lstB[1]== 40:
                print ('something something')
                break #out of EVERY loop
            else: #at this point I'm lost and can't refactor
                etc. (one extra comparison every time)  

一度に複数のループから抜け出す必要がある場合は、中断するのではなく、関数と戻りを考えてください。または例外と試行ブロックですが、不快に感じる人もいるかもしれません。

失敗フラグは機能しますが、あまりエレガントではありません。誇張された格言があります。これを次のように読んでください: 多くのレベルのインデントがある場合 (および一部の言語では他の言語よりも多くのレベルが必要な場合)、ロジックの一部を関数に移動できるかどうかを検討する必要があります。

また、いくつかの繰り返されるロジックをチェッカー関数に移動します。

(最後に、2 番目の for ループが最初の for ループにネストされているのはバグだと思います。同じイテレータ変数 H を持っているため、無限ループが発生すると思います。それを修正しました。)

#returns FALSE if a check fails, unlike the `quit` variable
def checker(lst, lstA):
    for i in range(4):
        if function(lst[i],lstA) != lst[i][1]: #testing FALSEHOOD
            return False;
    return True;


def main(???):
    for H in range(0,len(a_list)):
        if a_list[H] > lst[3][0]:
            continue

        lstA = [number_list[i]]

        if not checker(lst,lstA):
            continue

        lstA.append(input('some input from the user'))
        other_function(lstA)
        if lstA[1]== 40:
            print ('something something')
            return #break out of EVERY loop

    for H in range(0,len(a_list)):
        if not a_list[H] > lstA[0]:
            continue

        lstB = [number_list[i]]

        if checker(lst,lstB) and  function(lstA,lstB) == lstA[1]:
            lstB.append(input('some input from theuser'))
            other_function(lstB)
            if lstB[1]== 40:
                print ('something something')
                return # break out of EVERY loop
            else: #at this point I'm lost and can't refactor
                etc. (one extra comparison every time)  
于 2013-12-05T15:05:57.463 に答える