David Y.
—Many imperative programming languages support a switch
or case
control structure, which allows programmers to specify an arbitrary number of alternative code blocks to execute, depending on the value of a variable or expression. For example (pseudocode):
switch (hour) { case 13: print("It's one o'clock in the afternoon, time for lunch."); break; case 17: print("The workday is finished!"); break; case 8: print("Time for breakfast!"); break; default: print("An hour of no consequence."); break; }
Does Python have something equivalent?
The match-case
statement was introduced in Python 3.10, providing an official version of this control structure for the first time. The variable or expression provided to match
is tested against each pattern specified in an indented case statement.
We could implement the pseudocode above in Python as follows:
match hour: case 13: print("It's one o'clock in the afternoon, time for lunch.") case 17: print("The workday is finished!") case 8: print("Time for breakfast!") case _: # equivalent to "default case" -- this will be executed if nothing else matches print("An hour of no consequence.")
The above code uses literal values as match patterns, but match-case
supports a variety of additional, more complex patterns. Instead of matching literal values, we can use structural patterns to match an object’s type or structure:
match unknown_var: case str(): print("It's a string.") case [int(), str()]: print("It's a sequence of two values, an integer and a string.") case {"Apples": 3, "Oranges": 2}: print("It's a dictionary containing at least two known key-value pairs.") case [_, _, _]: print("It's a sequence of three values of any type.")
There are also capture patterns, which allow us to save and use the value of the matched expression:
match hour: case 13: print("It's one o'clock in the afternoon, time for lunch.") case 17: print("The workday is finished!") case 8: print("Time for breakfast!") case h: # the value of hour is stored in h print(f"The time is {h}")
We can even use structural and capture patterns together:
def count_products(products): match products: case p: print(f"1 product: {p}") case p, q: print(f"2 products: {p} and {q}") case p, q, r: print(f"3 products: {p}, {q} and {r}") count_products(["Apples"]) # will print "1 product: Apples" count_products(["Apples", "Oranges"]) # will print "2 products: Apples and Oranges" count_products(["Apples", "Oranges", "Bananas"]) # will print "3 products: Apples, Oranges, and Bananas"
Patterns can also have if
clauses, called guards. For example:
def count_products(products): match products: case p, q if p != q: print(f"Different products") case p, q: print(f"Duplicate products") count_products(["Apples", "Oranges"]) # will print "Different products" count_products(["Apples", "Apples"]) # will print "Duplicate products"
We can also use the logical or operator (|
) to include multiple alternative patterns in a single case
statement:
match hour: case 9 | 10 | 11 | 12: print("Workday, before lunch") case 13 | 14 | 15 | 16: print("Workday, after lunch")
Further examples are provided in the Python 3.10 release notes.
match-case
Prior to the introduction of match-case
in Python 3.10, the following alternatives were often used to emulate switch-case functionality.
if-elif
blocksif hour == 13: print("It's one o'clock in the afternoon, time for lunch.") elif hour == 17: print("The workday is finished!") elif hour == 8: print("Time for breakfast!") else: print("An hour of no consequence.")
switch_dict = { 13: lambda: print("It's one o'clock in the afternoon, time for lunch."), 17: lambda: print("The workday is finished!"), 8: lambda: print("Time for breakfast!") } switch_dict[hour]()
While this method is more syntactically similar to the switch-case
statement in other languages than chained elif
s, it cannot elegantly support a default case. If such a case is needed, the final line would have to be changed to the following:
if hour in switch_dict.keys(): switch_dict[hour]() else: print("An hour of no consequence.")
Tasty treats for web developers brought to you by Sentry. Get tips and tricks from Wes Bos and Scott Tolinski.
SEE EPISODESConsidered “not bad” by 4 million developers and more than 100,000 organizations worldwide, Sentry provides code-level observability to many of the world’s best-known companies like Disney, Peloton, Cloudflare, Eventbrite, Slack, Supercell, and Rockstar Games. Each month we process billions of exceptions from the most popular products on the internet.
Here’s a quick look at how Sentry handles your personal information (PII).
×We collect PII about people browsing our website, users of the Sentry service, prospective customers, and people who otherwise interact with us.
What if my PII is included in data sent to Sentry by a Sentry customer (e.g., someone using Sentry to monitor their app)? In this case you have to contact the Sentry customer (e.g., the maker of the app). We do not control the data that is sent to us through the Sentry service for the purposes of application monitoring.
Am I included?We may disclose your PII to the following type of recipients:
You may have the following rights related to your PII:
If you have any questions or concerns about your privacy at Sentry, please email us at compliance@sentry.io.
If you are a California resident, see our Supplemental notice.