0

I have a function, findnums(v) that is intended to append 5 numbers taken from user input to list v, which starts in main as an empty list. I have a nested try-except loop in my for loop for the function findnums(v) to try and reject non float user input.

I want my except condition to ignore the iteration that had the bad user input, not pass this bad input back to list v, and prompt the user to enter good input. While the condition doesn't pass bad input to the list, and does prompt the user to reenter good input, the bad data counts for an iteration and is not ignored. Ideally, I want the number of bad input iterations to be uncounted/infinite, and the number of good input iterations to always equal to 5.

Here is my code:

def main():
  v=[]
  findnums(v)
  printlist(v)
  

def findnums(v):
  for n in range(0,5):
    try:
      val=float(input('Please enter you number: '))          
      v.append(val)     
    except ValueError:  
        print("That is an invalid input, please start over.")  
        #main()
        #findnums(v) 
  return(v)
         

def printlist(v):
  print(v)

I've tried calling main() and the findnums(v) function in the except condition to have the program restart in the case of bad data, but in both cases it won't ignore the data as I want it to, but it will just rerun the program for each time the bad input is given, counting each piece of bad data for the final list. So if three pieces of bad data are entered, the program will ask for user input 12 time, and add those 12 items to the list v.

I think understand why this is happening. The data, good or bad is always being passed to v, I just can't think of a way of passing only good data to v.

  • Bad loop iterator, replace `for n in range(0,5)` with `while len(v)<5`. Use the length of accepted data as a terminator. – RufusVS Nov 10 '22 at 05:12
  • Possible duplicate of https://stackoverflow.com/questions/23294658/asking-the-user-for-input-until-they-give-a-valid-response – tripleee Nov 10 '22 at 06:30
  • @tripleee unintended, and my code uses a for loop and returns a variable to main, while that script does not have those features. – Samurai 425 Nov 10 '22 at 14:29
  • Those changes should be easy to apply if you know a little bit of Python. We can't have a new question for every case where the question only differs in minor details; the entire point of having duplicates is that they answer the _essence_ of the question. – tripleee Nov 10 '22 at 14:35
  • I'm pretty new to python, so my apologies for not recognizing those as minor. – Samurai 425 Nov 10 '22 at 15:20
  • @RufusVS didn't think of that, definitely better than how I set it up, thank you. Thank you all for your answers. – Samurai 425 Nov 10 '22 at 15:29

3 Answers3

0

I would use a while loop for this.

def main():
    v=[]
    findnums(v)
    printlist(v)

def findnums(v):
    # Reapeat the following until there is a break
    while(True):
        # If the list has a length of 5, break
        if len(v) == 5:
            break
        try:
            val = float(input('Please enter you number: '))
            v.append(val)
        except:
            print("That is an invalid input, please start over.") 

def printlist(v):
    print(v)
bop34
  • 61
  • 5
0

You may put the try/except block inside a while loop. That will keep asking the user for an input until they enter a float.

def main():
    v = []
    findnums(v)
    printlist(v)


def findnums(v):
    for i in range(5):
        while True:
            try:
                val = float(input('Please enter you number: '))
                v.append(val)
            except ValueError:
                print("That is an invalid input, please start over.")
    return v


def printlist(v):
    print(v)

Be careful passing an array to a function as arrays are passed by reference. For more info check: What's the difference between passing by reference vs. passing by value?

How I would reformat this is shown below

def findnums():
    v = []
    for i in range(5):
        while True:
            try:
                val = float(input('Please enter you number: '))
                v.append(val)
            except ValueError:
                print("That is an invalid input, please start over.")
            else:
                break
    return v


def main():
    v = findnums()
    print(v)


if __name__ == "__main__":
    main()
Dennis Sun
  • 48
  • 5
0

It's generally not advisable to pass in the array for modification, as this might accidentally expand the old array in repeated calls. Just return the array from the function:

def main():
  v = findnums(5)
  printlist(v)
  

def findnums(n):
  v=[]
  while len(v) < n:
    try:
      val=float(input('Please enter you number: '))          
      v.append(val)     
    except ValueError:  
        print("That is an invalid input, please start over.")  
  return(v)
         

def printlist(v):
  print(v)

main()
RufusVS
  • 4,008
  • 3
  • 29
  • 40