Python User Input
Most real programs don’t just run once with hard-coded values — they need to react to what a person types at the keyboard. Python’s built-in input() function is the standard way to pause a program, display a question, and read back whatever the user types. Whether you’re building a command-line calculator, a quiz, or a data-entry tool, input() is usually the first tool you reach for. This lesson explains exactly how input() works under the hood, how to convert and validate what it returns, and the mistakes almost every beginner makes with it at least once.
Overview: How input() Works
input() is a built-in function that does three things in sequence: it prints an optional prompt string to the screen, it pauses your program and waits for the user to type something and press Enter, and then it returns whatever was typed. The single most important fact about input() — and the source of most beginner bugs — is this: input() always returns a string (str), no matter what the user types. If the user types 42, Python does not hand you the integer 42; it hands you the three-character string "42". If you want to do arithmetic with it, you must convert it yourself using int(), float(), or another conversion function.
Because input() blocks execution, the rest of your program simply waits — nothing else runs until the user presses Enter. This makes it perfect for simple command-line interaction, but unsuitable for programs that need to keep doing other work while waiting for input (that requires more advanced tools like threads or async I/O, which are out of scope for basic user input).
Syntax
variable = input(prompt)
| Part | Description |
|---|---|
prompt |
Optional. A string printed to the screen before reading input. No newline is added automatically, so prompts usually end with a space or a colon and a space, like "Enter name: ". |
| Return value | Always a str, even if the user typed only digits. The trailing newline the user produced by pressing Enter is stripped off automatically. |
EOFError |
Raised instead of returning a value if the input stream ends before a line is read (for example, input piped from an exhausted file, or the user pressing Ctrl+D on Linux/macOS or Ctrl+Z on Windows). |
Examples
Example 1: A Simple Greeting
name = input("Enter your name: ")
print(f"Hello, {name}!")
Output: (assuming the user types Alice)
Enter your name: Alice
Hello, Alice!
The prompt "Enter your name: " is printed first, on the same line the user types on. Whatever the user typed — here, Alice — is stored in name as a string, and the f-string on the next line uses it to build the greeting.
Example 2: Converting Input for Arithmetic
first = input("Enter first number: ")
second = input("Enter second number: ")
total = int(first) + int(second)
print(f"The sum is {total}")
Output: (assuming the user types 4 then 7)
Enter first number: 4
Enter second number: 7
The sum is 11
Both calls to input() return strings, so int() is used to convert each one to an integer before adding them. Skipping this step is one of the most common beginner mistakes, covered below.
Example 3: Validating Input in a Loop
while True:
age_text = input("Enter your age: ")
if age_text.isdigit():
age = int(age_text)
break
print("Please enter a valid non-negative integer.")
if age >= 18:
print(f"You are {age} years old - you're an adult.")
else:
print(f"You are {age} years old - you're a minor.")
Output: (assuming the user types abc, then 17)
Enter your age: abc
Please enter a valid non-negative integer.
Enter your age: 17
You are 17 years old - you're a minor.
This is a realistic, production-style pattern: keep asking inside a while True loop until the input passes a check (here, str.isdigit()), and only then convert and break out of the loop. This guarantees the rest of the program never sees bad data.
Other Ways to Read Input
Reading Multiple Values on One Line
values = input("Enter numbers separated by spaces: ")
numbers = [int(x) for x in values.split()]
print(f"Sum: {sum(numbers)}")
Output: (assuming the user types 3 5 10)
Enter numbers separated by spaces: 3 5 10
Sum: 18
str.split() breaks the single line of text into a list of substrings on whitespace, and the list comprehension converts each piece to an integer. This pattern is extremely common for reading several numbers without calling input() repeatedly.
Reading Passwords Securely
from getpass import getpass
password = getpass("Enter your password: ")
print("Password received, length:", len(password))
Output: (assuming the user types hunter2, which is never echoed to the screen)
Enter your password:
Password received, length: 7
Regular input() echoes everything the user types, which is unsafe for passwords or other secrets. The getpass module’s getpass() function behaves like input() but suppresses the on-screen echo, so nothing appears as the user types.
Reading Input From a Pipe or File (sys.stdin)
When a program processes large amounts of input — for example, in scripting or competitive programming — reading line by line with sys.stdin (via for line in sys.stdin: or sys.stdin.readline()) is faster than repeated calls to input(), because it avoids the overhead of printing a prompt each time and works well with input redirected from a file.
Under the Hood: What Happens Step by Step
When you call input(prompt), CPython performs the following sequence:
- If a
promptargument was given, it is written to standard output (sys.stdout) immediately, without a trailing newline, and the stream is flushed so it appears on screen right away. - Python then reads from standard input (
sys.stdin) one line at a time, pausing your program’s execution until the user presses Enter. - The trailing newline character produced by pressing Enter is stripped from the text before it’s returned — you never see
\nat the end of aninput()result. - The remaining text is returned as a brand-new
strobject. No automatic type conversion happens at any point. - If the input stream reaches end-of-file before a newline is read (for example, stdin was redirected from an exhausted file), Python raises an
EOFErrorinstead of returning normally.
Common Mistakes
Mistake 1: Forgetting That input() Returns a String
Because input() always returns text, using the result directly in arithmetic fails or behaves unexpectedly:
age = input("Enter your age: ")
next_year = age + 1
print(f"Next year you will be {next_year}.")
This raises TypeError: can only concatenate str (not "int") to str, because age is a string and Python won’t silently add an integer to it. The fix is to convert explicitly with int():
age = int(input("Enter your age: "))
next_year = age + 1
print(f"Next year you will be {next_year}.")
Output: (assuming the user types 30)
Enter your age: 30
Next year you will be 31.
Mistake 2: Not Handling Invalid Input
Even after remembering to convert, a program can still crash if the user types something the conversion can’t handle:
count = int(input("How many items? "))
print(f"You have {count} items.")
If the user types five instead of a digit, int() raises ValueError: invalid literal for int() with base 10: 'five', crashing the whole program. Wrap the conversion in a try/except loop so bad input is caught and the user is asked again instead of the program dying:
while True:
raw = input("How many items? ")
try:
count = int(raw)
break
except ValueError:
print("That's not a valid number. Try again.")
print(f"You have {count} items.")
Output: (assuming the user types five, then 12)
How many items? five
That's not a valid number. Try again.
How many items? 12
You have 12 items.
Best Practices
- Always convert the result of
input()to the type you actually need (int(),float()) before doing math with it — never assume it’s numeric. - Validate user input with
try/exceptaround conversions, or with string methods likestr.isdigit(), before trusting it, and loop until the input is valid. - Use
str.strip()to remove accidental leading/trailing whitespace before comparing or converting user text. - Write clear, specific prompts that tell the user the expected format, e.g.
"Enter age (whole number): "rather than just"Age: ". - Use
getpass.getpass()instead ofinput()whenever you’re reading a password or other sensitive value, so it isn’t echoed to the screen. - Never pass user input into
eval()orexec()— doing so lets a malicious user run arbitrary code inside your program. - For reading several values at once, prefer
input().split()combined with a list comprehension ormap()over callinginput()in a loop. - Wrap repeated input-and-validate logic in a small function so it’s reusable and easy to test.
Practice Exercises
- Write a program that asks for the user’s name and their favorite number, then prints a single sentence combining both, such as
"Alice's favorite number is 7." - Write a program that repeatedly asks the user to enter a number and keeps a running total, stopping when the user types the word
doneinstead of a number. Hint: use a loop that breaks on the sentinel value"done"and otherwise converts and accumulates the input with atry/exceptaround the conversion. - Write a temperature converter that asks the user for a temperature in Celsius, validates that it’s a real number (rejecting non-numeric input with a friendly message and asking again), and then prints the equivalent value in Fahrenheit using the formula
F = C * 9/5 + 32.
Summary
input(prompt)prints an optional prompt, pauses the program, and returns whatever the user typed as astr— always a string, never a number.- Convert the returned string with
int(),float(), etc. before using it in arithmetic; forgetting this causesTypeErroror silent string concatenation instead of addition. - Invalid conversions raise
ValueError— guard against this withtry/exceptinside a loop that keeps asking until the input is valid. - If the input stream ends unexpectedly (piped file, Ctrl+D/Ctrl+Z),
input()raisesEOFErrorinstead of returning. - Use
str.split()to read several values from one line, andgetpass.getpass()to read sensitive values without echoing them to the screen. - Never feed raw user input into
eval()orexec()— it’s a serious security risk.
