The REPL is your debugger that's always on
Most languages have an interactive shell of some sort, but in Python it's a first-class part of how the language is used day-to-day. Not a teaching toy. The REPL is where you sketch ideas before writing the file, where you debug live objects without restarting your program, where you confirm "does this method actually return what I think?" before committing to a refactor.
The version that ships with Python 3.13 finally got proper multi-line editing, syntax highlighting, and a much improved help/exit experience. If you're on 3.13+, you've already got it. If you're on 3.12 or earlier, this lesson covers what to install (ipython, bpython) to get the same quality of life.
Built-in features you probably missed
Even the plain python REPL has features most people never discover:
- Up/Down arrow walks through your input history. Hit up — your last expression comes back, editable.
- Tab completes attribute names, method names, even local variables. Type
str.and hit tab — Python lists every method on str. - The
_(underscore) variable always holds the result of the last expression evaluated at the prompt. So you can type2 + 2, then_ * 10on the next line, and get 40. Chains like this are the REPL's superpower. help(thing)opens the docstring for any object — function, class, module. Pressqto exit help.dir(thing)lists every attribute and method on an object. Less polished than help, but exhaustive.
help() with no argument enters Python's full interactive help system — the same docs as docs.python.org, browsable from the prompt. Useful when offline or when you don't want to context-switch to a browser.
Multi-line editing in 3.13
Pre-3.13 REPLs had a famous wart — once you started typing a multi-line block (a function definition, a for-loop), you couldn't go back and edit earlier lines. Mistype something on line 1 of a five-line function? Cancel and re-type from scratch.
Python 3.13's new REPL fixes this. You can up-arrow into earlier lines of an in-progress block, edit them, and execute the whole thing. F1 brings up the help system inline. F2 brings up history search. F3 toggles paste mode (so you can paste indented code without the auto-indenter fighting you).
python -i script.py — script then drop into REPL
One of the highest-leverage flags in the entire python command. python -i myscript.py runs the script normally — and when it finishes (or crashes), drops you into a REPL where every variable, function, and class the script defined is still alive in your namespace.
This is how you debug a script without setting up pdb or any IDE: when something crashes, the traceback prints, and then >>> appears with full access to whatever state existed at crash time. Inspect, poke, fix, re-run.
python -i on a small repro script. The script crashes mid-stream; the REPL drops me in with the half-built response object still alive; I poke at it for two minutes and the bug is obvious. No debugger setup, no breakpoints — just a REPL with the corpse still warm.
ipython and bpython — REPLs with superpowers
Even with 3.13's improvements, two third-party REPLs are worth knowing:
- ipython — the data science REPL. Magic commands (
%timeit,%run,%load), better tracebacks, automatic pretty-printing, and integration with Jupyter notebooks.pip install ipythonthenipythonlaunches it. Once you've used%timeitfor benchmarking, the plain REPL feels primitive. - bpython — lightweight, lovely UI, inline auto-suggestions as you type. Less feature-loaded than ipython, but more pleasant for casual exploration.
pip install bpython.
You don't need both. Pick one (most devs end up on ipython) and add it to your default install kit.
exec() and eval() — when, why, and the security note
Two built-in functions occasionally tempt beginners — eval(string) evaluates a Python expression, exec(string) executes Python statements. Both take a string and run it as code.
The temptation: "I want the user to type a math expression and get the answer" → eval(input()). The reality: that one line lets the user type __import__('os').system('rm -rf ~') and your machine catches fire.
eval or exec. Ever. If you find yourself reaching for them to parse user input, what you actually want is ast.literal_eval (safe — only evaluates literals like numbers, strings, lists), or a real parser like pyparsing, or just json.loads if the input is JSON. eval on untrusted input is an arbitrary-code-execution vulnerability with extra steps.
That said, both functions have legitimate uses — runtime code generation, REPL implementations, dynamic class building. The Standard Library track will revisit them in context.
Bottom line
The REPL is not a beginner-only tool. Many seasoned Python developers spend more time in ipython than in their editor for exploratory work. Master the four basics (history, tab completion, _, help/dir), install ipython, and treat the REPL as your live debugger.
dir() and help() on it. The Pythonic answer to "how does this work?" is often "ask the object yourself."