简体   繁体   中英

How to stop python infinite loop?

import random   
n=int(input())  

array=[]     
for i in range(0,n): 
    flag=True    
    while flag:
           print("flag=",flag)
           a=[]
           for j in range(0,n):
               if i!=j:
                  w= random.randint(0,1)
                  print("random=",w)
                  if w==1 and i<j:
                     v=random.randint(1,10)
                     a.append(v)
                  else:
                      a.append(0)
               elif i==j:
                    a.append(0)
           print(a)
           if a.count(0) !=n:
              print("a.count(0)=",a.count(0))
              flag=False
              print("flag value=",flag)
      array.append(a)
print(array) 

In this program if the no of zeros not equal to n, it should break the loop and append it to the matrix but this loop is running infinite times, the value of the flag is assigned to false but still flag value will be true.This program is to generate atleast one random integer to each row so i am checking if the zeroes are not equal to no of columns break the loop.Is there any way to do that?

so plz tell me how to stop this loop when zeroes count is not equal to input n?

Okay, first off, let's fix the indentation and the PEP8 issues and add some type annotations so we can see what's going on. (Adding the type annotations helped me fix the indentation, since attempting to autofix it resulted in syntax errors that I had to go back and correct.) I just removed the Graph thing since you don't use it in this code anyway and I didn't know where that import was from.

import random
from typing import List

n = int(input())
array: List[List[int]] = []
for i in range(0, n):
    flag = True
    while flag:
        print("flag=", flag)
        a: List[int] = []
        for j in range(0, n):
            if i != j:
                w = random.randint(0, 1)
                print("random=", w)
                if w == 1 and i < j:
                    v = random.randint(1, 10)
                    a.append(v)
                else:
                    a.append(0)
            elif i == j:
                a.append(0)
        print(a)
        if a.count(0) != n:
            print("a.count(0)=", a.count(0))
            flag = False
            print("flag value=", flag)
    array.append(a)
print(array)

Now let's look at the output:

2
flag= True
random= 0
[0, 0]
flag= True
random= 1
[0, 6]
a.count(0)= 1
flag value= False
flag= True
random= 0
[0, 0]
flag= True
random= 1
[0, 0]
flag= True
random= 0
[0, 0]
flag= True
random= 0
[0, 0]
flag= True

So, we do break the inner while loop the first time through the for i loop (i=0), but we come back and restart it in each iteration of the for i , and on the second time (i=1), we always end up with a == [0] * n . When I tried this with higher values of n it seemed like we always end up in this state.

So, what are we doing in that for j loop that always results in an array full of zeroes when we're on the last i ? Well, it all comes down to this block:

                w = random.randint(0, 1)
                print("random=", w)
                if w == 1 and i < j:
                    v = random.randint(1, 10)
                    a.append(v)
                else:
                    a.append(0)

Both i and j are iterations over the same range(n) . When i is on the last iteration (ie i == n - 1 ), then it will never be possible to have i < j because i is already at the maximum value that either of them can have. That means that we will always do a.append(0) regardless of the value of w , and will therefore always end up with an array of all zeroes no matter how many times we go through that while loop.

On the final i iteration, flag remains True because it will always be true that a.count(0) == n , and so the while flag loop within the last time around on that for i loop will never terminate.

One way to help prove this to ourselves is to simply add an assert , like this:

                if w == 1 and i < j:
                    # This block is the only thing that can ever set flag to False!
                    assert i < n - 1, "We never get here on the last loop!"
                    v = random.randint(1, 10)
                    a.append(v)

and observe that this never results in an AssertionError .

Python does not carry on infinite loops as It has protective measures against this.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM