Demystifying Python's Slash Syntax: What Does `lambda x, /:` Actually Mean?
What Does the Slash (/) Mean in Python?
If you have recently stumbled across Python code resembling f = lambda x, /: x, you might wonder what kind of esoteric operator ,/: is. First, let us clear up a common misconception: ,/: is not an operator.
Instead, what you are seeing is the comma separator (,), the positional-only parameter marker (/), and the colon (:) that separates a lambda's parameter list from its return expression.
Introduced in Python 3.8 via PEP 570, the slash / designates that all arguments defined before it are positional-only parameters.
Is lambda x, /: x Identical to lambda x: x?
The short answer is no. While both functions return the value you pass into them, they behave differently depending on how you pass that value.
Example 1: The Standard Function (lambda x: x)
In standard Python functions, arguments can be passed either positionally or as keyword arguments:
f = lambda x: x
# Calling positionally:
print(f(42)) # Output: 42
# Calling via keyword:
print(f(x=42)) # Output: 42
Example 2: The Positional-Only Function (lambda x, /: x)
When you insert the slash /, Python explicitly forbids callers from using the parameter name as a keyword:
f = lambda x, /: x
# Calling positionally:
print(f(42)) # Output: 42
# Calling via keyword:
print(f(x=42))
# Raises TypeError: <lambda>() got some positional-only arguments passed as keyword arguments: 'x'
Why Do Positional-Only Parameters Exist?
While seeing / inside a lambda is somewhat rare, positional-only arguments serve essential purposes in modern Python design:
- API Stability: When designing a library or API, specifying arguments as positional-only allows you to rename the internal parameter in future versions without breaking consumer code that might have used the keyword name (e.g., changing
xtoval). - Mirroring Built-in Functions: Many built-in C functions in Python (such as
len(),abs(), orpow()) have historically rejected keyword arguments. PEP 570 allows pure Python functions to mirror this exact behavior. - Preventing Ambiguity: If a function takes
**kwargsto capture arbitrary keyword arguments, a positional-only parameter prevents collisions where the keyword dictionary happens to include the name of an existing parameter.
Syntax Overview: Combining / and *
Python gives you full control over how arguments are passed by combining the positional-only delimiter (/) and the keyword-only delimiter (*):
def example(pos_only, /, standard, *, kw_only):
pass
pos_only: Must be passed positionally (e.g.,example(1, ...)).standard: Can be passed positionally or as a keyword (e.g.,example(1, 2, ...)orexample(1, standard=2, ...)).kw_only: Must be passed by keyword (e.g.,example(1, 2, kw_only=3)).
Summary
The code lambda x, /: x defines an anonymous function where argument x must strictly be provided positionally. Attempting to call it as f(x=5) will throw a TypeError, setting it apart from the conventional lambda x: x.