Home > front end >  Python | while is repeating old data, even if False
Python | while is repeating old data, even if False

Time:07-05

I'm trying to create a loop if the condition is not met. If it is met at minimum second run, the print from my last run is also in my output, like in the example its printing the same print() that was printed in the previous run in addition to the result of the second run.

secretcode= r.randint(1, 100)

print("\n\n\nWelcome to the lottery!\n")
print("Guess a number from 1 to 100!")
print(secretcode)


def usrinput():
    usrinputnumber = int(input("Your number: "))
    schleife(usrinputnumber)


def schleife(usrinputnumber):
    while not (secretcode == usrinputnumber):
        if usrinputnumber > secretcode:
            print("Awh damn! Your number is too high!!")
            usrinput()

        else:
            print("Unlucky! YOur number is too low!")
            usrinput()


    print("Congratz! You guessed the number!!")


usrinput()

Everything works fine when I do an "if" instead the while and using the last print as "else"

Example: The "secretcode" is 55. As input I type 45. The console prints "Unlucky! The number is too low!" Now I type 55. The console prints the "Congratz" message AND the "too low" message. Why the "too low" message?

I know functions are not needed, I just wanna know what the problem is and if I can run it in functions like I did.

Thank you very much!

CodePudding user response:

This control flow does not make any sense. Please keep in mind that calling a function is not at all like telling the code to "go here next". It is a request to compute a result, which you will then use in the current context. It is also important to understand that each call to a function is a separate process. The function is not like a machine that is set in motion when called, but instead like a set of instructions that will be followed by a new executor, each time.


When usrinput() is called from within schleife, right now usrinput will call schleife again. That separate call has its own complete set of local variables, including the usrinputnumber parameter. Supposing that the user typed the correct secretcode, this call to schleife will escape its while loop, print the success message...

... and then return back the result of its computation (which is None) to its caller, the call of usrinput, which returns its result (also None) to the other call of schleife, which also hadn't finished yet. And, within that call, nothing has changed its local value for usrinputnumber, so the loop continues.


Remember that functions are supposed to do one thing. The purpose of usrinput is to get the user's input. The task performed by schleife is not a logical part of that task, therefore usrinput should not call schleife.

Instead: usrinput, instead of trying to feed the result of its computation (i.e., the user's input) to the "next step", should return that result - that is what return is for.

On the other hand, schleife can still call usrinput, because "get new user input to see if it matches this time" is a logical part of its task. Since the value will be returned, we need to make use of that by explicitly assigning it to usrinputnumber. We can also see that since schleife will be calling usrinput in the loop anyway, it makes as much sense to get the initial value that way, too.


Putting it together, we get:

def usrinput():
    return int(input("Your number: "))

def schleife():
    usrinputnumber = usrinput()
    while not (secretcode == usrinputnumber):
        if usrinputnumber > secretcode:
            print("Awh damn! Your number is too high!!")
            usrinputnumber = usrinput()
        else:
            print("Unlucky! YOur number is too low!")
            usrinputnumber = usrinput()
    print("Congratz! You guessed the number!!")

schleife()
  • Related