6
\$\begingroup\$

I am just starting coding, and this is my attempt at the famous number-guessing game. Any and all feedback and criticism is greatly appreciated.

print(" Welcome to the number guessing game")
play_game = True
while play_game:
    import random
    random_integer1 = random.randint(0, 50)
    random_integer2 = random.randint(random_integer1+5, 100)
    print("Your number are between ", random_integer1, random_integer2)
    random_integer = random.randint(random_integer1, random_integer2)
    running = True
    while running:
        number = int(input("what is your guess?"))
        if number == random_integer:
            running = False
            print("Correct first try")
        if number != random_integer:
            if number > random_integer:
                print(" Too high, guess again")
            if number < random_integer:
                print(" Too low, guess again")
            number = int(input("what is your guess?"))
            redemption = True
            while redemption:
                count = 1
                guess_count = 1
                while count < 11:
                    if number != random_integer:
                        count += 1
                        guess_count += 1
                        if number > random_integer:
                            print(" Too high, guess again")
                        if number < random_integer:
                            print(" Too low, guess again")
                        if count == 10:
                            coward_protocol = input("do you want to give up? (y/n)")
                            if coward_protocol == 'y':
                                redemption = False
                                running = False
                                print("Goodbye Coward")
                                break
                            else:
                                count -=10
                        number = int(input("what is your guess?"))
                    if number == random_integer:
                        redemption = False
                        running = False
                        print("Correct, only took you", guess_count+1, "tries!")
                        break
    play_again = input(" Do you want to play again? (y/n)")
    if play_again == 'y':
        play_game = False
        play_game = True
    else:
        print("Have a good day!")
        break
\$\endgroup\$

2 Answers 2

7
\$\begingroup\$

I enjoyed playing the game! There are a few suggestions I would like to make that would make the code more maintainable and possibly improve the user's experience.

Don't Repeat Yourself (DRY)

Your code is fairly complex as written. By introducing functions that implement smaller pieces of logic, the code becomes more readable and thus maintainable and you also avoid duplicating operations. Specifically:

  1. There are several places where you solicit a number from the user with the prompt "what is your guess?". If the user inputs something that is not a legitimate number, the program raises a ValueError exception and terminates. To prevent this you could do one of two things: (1) Validate that the input string consists of only digits or (2) Use try/except blocks around the code hat does the string to integer conversion and catch the exception. On invalid input you should print a message telling the user "Invalid integer input; please try again." and then re-issue the input statement. Thus you will end up having to code a loop out of which you break when the user enters a valid input. I would therefore suggest you create a function called, for instance, input_guess. This function takes as arguments the minimum valid integer that can be input and the maximum valid integer. If the user specifies something that cannot be converted to an integer or the number is not in the valid range, then a suitable error message is outputted.
  2. Likewise, there are multiple places where you output a prompt that needs to be answered by "y" or "n". You could create a function, e.g. input_yes_or_no, that puts out the passed prompt and accepts as input "y", "Y", "n" or "N". If the user inputs something else, an error message is produced and the prompt is put out again.

Follow the PEP 8 Style Guide for Python

Your import statement is better placed at the top of the source following a docstring that describes what the program does.

Remove Checks that Are Unnecessary

You have:

        if number != random_integer:
            if number > random_integer:
                print(" Too high, guess again")
            if number < random_integer:
                print(" Too low, guess again")

This should be:

        if number != random_integer:
            if number > random_integer:
                print(" Too high, guess again")
            else:
                print(" Too low, guess again")

You have:

    if play_again == 'y':
        play_game = False
        play_game = True
    else:
        print("Have a good day!")
        break

This should be:

    if play_again == "n":
        print("Have a good day!")
        break

You can code strings using single or double quotes, but generally it is better to stick with one style of quoting.

Simplify the Logic

You do not need flags such as play_game and running; you can instead be using while True: blocks with appropriate break statements.

You do not need both count and guess_count variables. You can determine when to ask the user if they want to give up whenever guess_count % 10 == 0. And if count is 10, why would you reset it back to 0 with count -= 10 instead of count = 0?

Improved Prompting

I am not sure why you are using single-space indentation on some of your output; I don't think it is makes anything clearer. I suggest your prompts be complete sentences starting with a capital letter and ending with a period followed by a single space so that the user's response is separated by the question. Allow the user to input "y" or "Y" for "yes" and "n" or "N" for "No". After a user makes a guess that is either too high or too low, the next prompt for input should specify what the new valid range of input is.

If you had the following functions, how could you greatly simplify the code?

def input_guess(min_number: int, max_number: int) -> int:
    """Prompt the user for a number and return it if
    it is valid and within the proper range."""
    while True:
        try:
            number = int(input(f"\nYour number is between {min_number} and {max_number}. What is your guess? "))
        except ValueError:
            print('You did not input a valid integer.')
        else:
            if min_number <= number <= max_number:
                return number
            print("Your input was not in the valid range.")

def input_yes_or_no(prompt: str) -> str:
    """Output the passed prompt and accept an abbreviated "Yes" or "No"
    response."""
    while True:
        answer = input(prompt).lower()
        if answer == 'y' or answer == 'n':
            return answer
        print('Invalid response.')
\$\endgroup\$
6
\$\begingroup\$

This is a good first question and a good first coding attempt!

Layout

Conventionally the imports are placed at the top of the file, before any other statements:

import random

print(" Welcome to the number guessing game")
play_game = True

The code is very consistent in its use of whitespace (indentation, space around operators, etc.). However, there are a couple places which could be slightly improved. The black program can be used to automatically add consistency.

UX

When I run the code, I get this prompt:

Your number are between

That wording is a little awkward. Consider this instead:

print(f"Guess a number between {random_integer1} and {random_integer2}")

Note that it uses an f-string to simplify the code.

For input prompts, I like to add a single space at the end of the text so that there will be a space between the text and my input on my screen:

number = int(input("what is your guess? "))

It is great that you specifically give the user the expected options for input ("y/n"). It is also common to allow input to be case-insensitive by calling lower():

play_again = input(" Do you want to play again? (y/n) ").lower()

Ouch!

Goodbye Coward

Be nice to your users so they'll want to come back and play again :)

Simpler

Here is another print line:

print("Correct, only took you", guess_count+1, "tries!")

which is commonly written using an f-string

print(f"Correct, only took you {guess_count+1} tries!")

In this code:

if play_again == 'y':
    play_game = False
    play_game = True

the following line is not needed and should be deleted:

    play_game = False

These 2 if statements:

if number > random_integer:
    print(" Too high, guess again")
if number < random_integer:
    print(" Too low, guess again")

can be simplified as an if/else:

if number > random_integer:
    print(" Too high, guess again")
else:
    print(" Too low, guess again")

There is no need for the extra check since you already checked for equality earlier on.

The same is true here:

if number == random_integer:
    running = False
    print("Correct first try")
if number != random_integer:

This is simpler:

if number == random_integer:
    running = False
    print("Correct first try")
else:

DRY

You have duplicate code in a couple places, specifically where you ask for input, then check if the number is correct or not. Consider breaking your code into some functions for that. For example:

def print_result(guess, target):
    """
    Print if guess is too high or low.
    Assumes they were already checked for equality.
    """
    if guess > target:
        print(" Too high, guess again")
    else:
        print(" Too low, guess again")

Documentation

The PEP 8 style guide recommends adding a docstring at the top of the code.

"""
Number-guessing game

Here's how you play... add description here
"""
\$\endgroup\$
1
  • \$\begingroup\$ I appreciate the feedback! I will definitely be implementing more f-strings in my upcoming projects, and will make it a priority to make more user-friendly code ! Thank ya! \$\endgroup\$ Commented Oct 2 at 20:33

You must log in to answer this question.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.