Python compile Modes: exec vs eval vs single Explained
Python's built-in compile() function transforms source
code strings into executable code objects that can later be passed to
exec() or eval(). The behavior of this
function is fundamentally governed by its mode parameter,
which accepts one of three arguments: 'exec',
'eval', or 'single'. This parameter instructs
the Python parser how to interpret the input syntax, what return
behavior to expect, and how to handle expressions during execution.
The exec Mode
The 'exec' mode is designed for compiling arbitrary
Python code, mimicking the execution of a standard Python module or
script.
- Syntax Allowed: It accepts any valid Python code, including multiple statements, variable assignments, loops, class definitions, and function declarations.
- Return Value: Code compiled in this mode returns
Noneupon execution. If expressions within the code yield results, those results are discarded unless explicitly assigned to a variable or passed to an output function likeprint(). - Typical Use Case: Running entire scripts, code blocks, or dynamic program definitions.
code_exec = compile("x = 5\ny = 10\nresult = x + y", "<string>", "exec")
namespace = {}
exec(code_exec, namespace)
print(namespace["result"]) # Outputs: 15The eval Mode
The 'eval' mode strictly expects a single Python
expression and evaluates it to produce a direct result.
- Syntax Allowed: It accepts only expressions (e.g.,
2 + 2,[x for x in range(5)], or a variable name). It explicitly rejects statements, assignments (likex = 5), loops, or compound structures; attempting to include statements will raise aSyntaxError. - Return Value: When executed using
eval(), the resulting code object computes and directly returns the evaluated value of the expression. - Typical Use Case: Evaluating mathematical formulas, dynamically resolving variable lookups, or parsing simple condition strings.
code_eval = compile("5 * 10 + 2", "<string>", "eval")
output = eval(code_eval)
print(output) # Outputs: 52The single Mode
The 'single' mode emulates the behavior of the
interactive Python interpreter (the REPL).
- Syntax Allowed: It is meant for compiling a single interactive statement. If multiple statements are provided across newlines, the parser stops processing after the first statement or raises an error if trailing code is detected. However, multiple statements joined on a single line with semicolons are permitted.
- Return Value and Side Effects: If the compiled
statement evaluates to an expression, running it with
exec()will automatically print the result to standard output (viasys.displayhook) as long as the value is notNone. - Typical Use Case: Building custom interactive command-line environments, debuggers, or shell implementations.
code_single = compile("40 + 2", "<string>", "single")
exec(code_single) # Automatically prints: 42Key Differences Summary
| Feature | exec |
eval |
single |
|---|---|---|---|
| Input Structure | Multiple statements or script blocks | Exactly one expression | A single statement or semicolon-separated line |
| Allows Statements? | Yes (loops, definitions, assignments) | No (raises SyntaxError) |
Yes (typically single-line) |
| Execution Output | Returns None |
Returns the expression result | Displays the expression result if not
None |
| Primary Consumer | exec() |
eval() |
exec() |