Number Guessing Game with AI
Abstract
This project takes the classic “Guess the Number” game and flips it on its head: first the computer guesses your number, then you guess the computer’s number, and whoever needs fewer rounds wins. The interesting part is that the computer does not guess randomly — it uses binary search, an algorithm that guarantees it can find any integer between 0 and 100 in at most seven guesses. Watching it work is one of the best practical introductions to algorithmic thinking.
You will learn:
- How binary search works step-by-step.
- Why algorithm choice matters: random guessing might take 100 tries, binary search takes seven.
- The concept of logarithmic time complexity (
O(log n)O(log n)). - How to structure a two-phase game with score comparison.
- How to extend the “AI” with more sophisticated strategies.
Why Binary Search Is Magic
Imagine you are looking for a word in a dictionary. You do not start at “A” and read every page. You open it in the middle. If your word comes later in the alphabet, you ignore the first half and repeat with the second half. Each step halves the problem.
That is exactly what the AI does:
| Round | Range | Mid | Your answer | New range |
|---|---|---|---|---|
| 1 | 0–100 | 50 | “lower” | 0–49 |
| 2 | 0–49 | 25 | “higher” | 26–49 |
| 3 | 26–49 | 37 | “lower” | 26–36 |
| 4 | 26–36 | 31 | “higher” | 32–36 |
| 5 | 32–36 | 34 | “yes” | done |
In 5 guesses out of 101 possible numbers. Random guessing would have averaged about 50 attempts.
Mathematically, binary search uses about log₂(n)log₂(n) guesses for nn numbers. log₂(101) ≈ 6.66log₂(101) ≈ 6.66, so at most 7 — always.
Prerequisites
- Python 3.6 or above.
- A text editor or IDE.
- Comfort running scripts and reading basic Python.
- Familiarity with conditionals and loops.
Concepts You Will Use
random.randint(a, b)random.randint(a, b)— pick a random integer for the human-to-guess phase.whilewhileloop with a shrinking range — the core of binary search.- Integer division
////—(low + high) // 2(low + high) // 2gives the midpoint without floats. - Input validation — making sure the player’s hint is
hh,ll, oryy. - Counter variables — track how many rounds each side took.
Getting Started
Create the project
- Create a folder named
number-guessing-ainumber-guessing-ai. - Inside it, create
numberguessingwithai.pynumberguessingwithai.py.
Write the code
Number Guessing Game with AI
Source# Number Guessing Game with AI
# Credits: https://gist.github.com/ashishanand7/61bb95a556e1575a63b1745c5fd48a4a
import random
print("NUMBER GUESSING GAME . YOU vs AI \n AI's turn is first\n")
print('Think of a number a number between 0 and 100. ')
input('Press Enter when done')
m=50
j=100
i=0
c=0
print('\nAnswer with:\n "h" if your number is bigger.\n "l" if your number is smaller.\n "y" if AI guesses the correct number')
while True:
x=input('is it '+str(m)+' ?\n')
c+=1
if x=="y":
print("BINGO")
break
elif x=="h":
i=m
m=round(((m+j)/2),0)
elif x=="l":
j=m
m=round(((m+i)/2),0)
else:
print("Invalid input")
c-=1
print("Now it's your turn to guess which number computer has thought of between 0 and 100")
a=random.randint(0,101)
d=0
while True:
x=int(input('Tell which number AI has picked between 0 & 100\n'))
d+=1
if x==a:
print('BINGO . You guessed right.')
break
elif x<a:
print('you guessed too low .')
elif x>a:
print('you guessed too high .')
if c<d:
print("The AI guessed it in ",c," rounds while you took ",d," rounds .\n AI WINS :D\n Robots are your Overlords . Accept it !!!")
elif c==d:
print("Both AI & you took ",c," rounds . So , it's a TIE :|")
else:
print("The AI guessed it in ",c," rounds while you took ",d," rounds .\nYOU WON :\ \nSavour the few wins left before robots outsmart you forever ...")# Number Guessing Game with AI
# Credits: https://gist.github.com/ashishanand7/61bb95a556e1575a63b1745c5fd48a4a
import random
print("NUMBER GUESSING GAME . YOU vs AI \n AI's turn is first\n")
print('Think of a number a number between 0 and 100. ')
input('Press Enter when done')
m=50
j=100
i=0
c=0
print('\nAnswer with:\n "h" if your number is bigger.\n "l" if your number is smaller.\n "y" if AI guesses the correct number')
while True:
x=input('is it '+str(m)+' ?\n')
c+=1
if x=="y":
print("BINGO")
break
elif x=="h":
i=m
m=round(((m+j)/2),0)
elif x=="l":
j=m
m=round(((m+i)/2),0)
else:
print("Invalid input")
c-=1
print("Now it's your turn to guess which number computer has thought of between 0 and 100")
a=random.randint(0,101)
d=0
while True:
x=int(input('Tell which number AI has picked between 0 & 100\n'))
d+=1
if x==a:
print('BINGO . You guessed right.')
break
elif x<a:
print('you guessed too low .')
elif x>a:
print('you guessed too high .')
if c<d:
print("The AI guessed it in ",c," rounds while you took ",d," rounds .\n AI WINS :D\n Robots are your Overlords . Accept it !!!")
elif c==d:
print("Both AI & you took ",c," rounds . So , it's a TIE :|")
else:
print("The AI guessed it in ",c," rounds while you took ",d," rounds .\nYOU WON :\ \nSavour the few wins left before robots outsmart you forever ...")Run it
C:\Users\username\Documents\number-guessing-ai> python numberguessingwithai.py
Think of a number between 0 and 100!
Is your number 50? (h/l/y): h
Is your number 75? (h/l/y): l
Is your number 62? (h/l/y): l
Is your number 56? (h/l/y): y
I guessed your number in 4 rounds!
Now guess my number between 0 and 100:
50
Too low! Try again: 75
Too high! Try again: 62
Correct! You guessed my number in 3 rounds!
You win this round!C:\Users\username\Documents\number-guessing-ai> python numberguessingwithai.py
Think of a number between 0 and 100!
Is your number 50? (h/l/y): h
Is your number 75? (h/l/y): l
Is your number 62? (h/l/y): l
Is your number 56? (h/l/y): y
I guessed your number in 4 rounds!
Now guess my number between 0 and 100:
50
Too low! Try again: 75
Too high! Try again: 62
Correct! You guessed my number in 3 rounds!
You win this round!Step-by-Step Explanation
1. Set up randomness
import randomimport randomUsed for the second phase, where you have to guess a random number the computer generates.
2. The AI’s binary-search loop
low, high = 0, 100
ai_rounds = 0
while True:
ai_rounds += 1
guess = (low + high) // 2
response = input(f"Is your number {guess}? (h/l/y): ").lower()
if response == "y":
break
elif response == "h": # actual number is higher
low = guess + 1
elif response == "l": # actual number is lower
high = guess - 1
else:
print("Please answer h, l, or y.")
ai_rounds -= 1 # do not count this round
print(f"I guessed your number in {ai_rounds} rounds!")low, high = 0, 100
ai_rounds = 0
while True:
ai_rounds += 1
guess = (low + high) // 2
response = input(f"Is your number {guess}? (h/l/y): ").lower()
if response == "y":
break
elif response == "h": # actual number is higher
low = guess + 1
elif response == "l": # actual number is lower
high = guess - 1
else:
print("Please answer h, l, or y.")
ai_rounds -= 1 # do not count this round
print(f"I guessed your number in {ai_rounds} rounds!")How this works:
(low + high) // 2(low + high) // 2is the midpoint.////is integer division, so the result is always a whole number.- If the player says “higher”, the answer must be above
guessguess, so we setlow = guess + 1low = guess + 1. We use+ 1+ 1becauseguessguessitself was just ruled out. - If “lower”, we set
high = guess - 1high = guess - 1for the same reason. - If “yes”, we win and
breakbreak. - The unknown-input branch undoes the round counter to avoid penalizing the AI for the player’s typo.
3. The human’s turn
secret = random.randint(0, 100)
human_rounds = 0
while True:
human_rounds += 1
try:
guess = int(input("Your guess: "))
except ValueError:
print("Please enter a whole number.")
human_rounds -= 1
continue
if guess == secret:
print(f"Correct! You guessed my number in {human_rounds} rounds!")
break
print("Too low!" if guess < secret else "Too high!")secret = random.randint(0, 100)
human_rounds = 0
while True:
human_rounds += 1
try:
guess = int(input("Your guess: "))
except ValueError:
print("Please enter a whole number.")
human_rounds -= 1
continue
if guess == secret:
print(f"Correct! You guessed my number in {human_rounds} rounds!")
break
print("Too low!" if guess < secret else "Too high!")random.randint(0, 100)random.randint(0, 100)picks the secret number once, before the loop.int(input(...))int(input(...))is wrapped intry/excepttry/exceptso letters or empty input do not crash the game.- A ternary expression (
"Too low!" if … else "Too high!""Too low!" if … else "Too high!") avoids the need for a fullif/elseif/elseblock on that line.
4. Pick the winner
if ai_rounds < human_rounds:
print("AI wins — it guessed faster.")
elif human_rounds < ai_rounds:
print("You win!")
else:
print("Tie!")if ai_rounds < human_rounds:
print("AI wins — it guessed faster.")
elif human_rounds < ai_rounds:
print("You win!")
else:
print("Tie!")Complexity Notes
Binary search has time complexity O(log n). For range nn:
| n | Max rounds (⌈log₂ n⌉ + 1⌈log₂ n⌉ + 1) |
|---|---|
| 10 | 4 |
| 100 | 7 |
| 1,000 | 10 |
| 1,000,000 | 20 |
| 1,000,000,000 | 30 |
Doubling the range adds one extra round. That is why binary search underlies sorted-collection lookups, version-control bisect, and many machine-learning hyperparameter searches.
Random guessing would be O(n) — proportional to the size of the range. Even 1,000 numbers gets painful.
Robust Input
In the AI phase, an unfair player might say “higher” when their number is actually lower. The AI cannot detect that — the bug shows up as an empty range:
if low > high:
print("Hmm, your answers don't add up. Did you switch your number?")
breakif low > high:
print("Hmm, your answers don't add up. Did you switch your number?")
breakAdd that check inside the AI loop and the game ends gracefully when the search collapses.
Common Mistakes
| Problem | Cause | Fix |
|---|---|---|
| AI keeps guessing the same number | Forgot + 1+ 1 / - 1- 1 when shrinking the range | low = guess + 1low = guess + 1 and high = guess - 1high = guess - 1 |
| Range crashes after many rounds | Player gave conflicting hints | Detect low > highlow > high and exit politely |
| AI guesses outside 0–100 | Off-by-one in initial range | Initialize low, high = 0, 100low, high = 0, 100, not 1, 991, 99 |
| Tie always favors AI | You used << not <=<= | Use a separate elifelif for the tie case |
Variations to Try
1. Adjustable range
Ask the player for the range at the start:
low_input = int(input("Lower bound: "))
high_input = int(input("Upper bound: "))low_input = int(input("Lower bound: "))
high_input = int(input("Upper bound: "))2. Best-of-three rounds
Wrap the whole game in a loop that tracks total wins:
ai_wins = human_wins = 0
for round_num in range(1, 4):
play_one_round()
# tally
print(f"Series winner: {'AI' if ai_wins > human_wins else 'You'}")ai_wins = human_wins = 0
for round_num in range(1, 4):
play_one_round()
# tally
print(f"Series winner: {'AI' if ai_wins > human_wins else 'You'}")3. Smarter “AI” strategies
- Random AI — guess uniformly at random; great baseline.
- Pattern AI — bias toward numbers humans pick often (lots of 7s and 17s).
- Adaptive AI — track which numbers the player has used in past games and avoid them.
4. Hide the binary search behind a “thinking” delay
import time
print("Thinking...", end="", flush=True); time.sleep(0.5)import time
print("Thinking...", end="", flush=True); time.sleep(0.5)Adds personality without slowing gameplay.
5. Add a GUI
Tkinter with two number-entry fields and a big “Guess!” button. Display the AI’s current range visually.
6. Compare algorithms head-to-head
Run binary search vs. random guessing 10,000 times each, average the rounds, and graph the result with matplotlibmatplotlib.
7. Multiplayer scoreboard
Persist round counts in a JSON file. Each session you can see your improvement vs. the AI.
Real-World Algorithm Examples
Binary search shows up everywhere:
bisectbisectmodule in Python’s standard library — insert into a sorted list in O(log n).git bisectgit bisect— finds which commit introduced a bug by binary-searching commits.- Database B-tree indexes — searches narrow the range repeatedly.
- Auto-tuning compilers — find the largest input size that still fits a time budget.
- Numerical methods — bisection for root-finding (e.g., solving
f(x) = 0f(x) = 0).
Educational Value
This project teaches:
- Algorithmic thinking — pick a strategy, prove an upper bound, implement it.
- Trade-offs — the AI is fast and fair; a random guesser is simpler but slower.
- Logarithmic growth — intuition for one of the most important concepts in computer science.
- State management —
lowlowandhighhightogether represent the AI’s belief about the answer. - Robust input handling — protecting against bad data and inconsistent answers.
Next Steps
- Implement a graphical version with a number line that shrinks each round.
- Build a command-line tournament: a dozen different AI strategies competing.
- Try the 20 Questions variant: yes/no questions over a database of objects.
- Read about interpolation search — even faster when data is uniformly distributed.
- Move on to the Hangman project for a different style of search.
Conclusion
You implemented binary search from scratch, paired it with a human-vs-computer game loop, and saw why one good algorithm beats brute force every time. The same idea — halve the problem at each step — drives most of the fast lookup code you will ever touch. Full source on GitHub. More beginner projects on Python Central Hub.
If this helped you, consider buying me a coffee ☕
Buy me a coffeeWas this page helpful?
Let us know how we did
