Python match case
Python 3.10 引入了 match 語句,類似於其他語言的 switch,但功能更強大,支援結構化模式比對 (structural pattern matching)。
基本語法
match 變數:
case 模式1:
# 匹配時執行
case 模式2:
# 匹配時執行
case _:
# 預設情況(都不匹配時)
status = 404
match status:
case 200:
print("OK")
case 404:
print("Not Found")
case 500:
print("Internal Server Error")
case _:
print("Unknown status")
輸出:
Not Found
_ 是萬用字元,匹配任何值,類似於其他語言的 default。匹配多個值
使用 | 匹配多個值:
status = 301
match status:
case 200 | 201 | 202:
print("Success")
case 301 | 302:
print("Redirect")
case 400 | 401 | 403 | 404:
print("Client Error")
case 500 | 502 | 503:
print("Server Error")
case _:
print("Unknown")
匹配序列
point = (0, 1)
match point:
case (0, 0):
print("Origin")
case (0, y):
print(f"On Y-axis at y={y}")
case (x, 0):
print(f"On X-axis at x={x}")
case (x, y):
print(f"Point at ({x}, {y})")
輸出:
On Y-axis at y=1
匹配不定長度序列
numbers = [1, 2, 3, 4, 5]
match numbers:
case []:
print("Empty list")
case [x]:
print(f"Single element: {x}")
case [x, y]:
print(f"Two elements: {x}, {y}")
case [first, *rest]:
print(f"First: {first}, Rest: {rest}")
輸出:
First: 1, Rest: [2, 3, 4, 5]
匹配字典
data = {"action": "create", "name": "Alice"}
match data:
case {"action": "create", "name": name}:
print(f"Creating user: {name}")
case {"action": "delete", "id": user_id}:
print(f"Deleting user with id: {user_id}")
case {"action": action}:
print(f"Unknown action: {action}")
case _:
print("Invalid data")
輸出:
Creating user: Alice
加上條件 (Guard)
使用 if 加上額外條件:
point = (3, 4)
match point:
case (x, y) if x == y:
print(f"On diagonal at ({x}, {y})")
case (x, y) if x > 0 and y > 0:
print(f"In first quadrant at ({x}, {y})")
case (x, y):
print(f"At ({x}, {y})")
輸出:
In first quadrant at (3, 4)
匹配物件
class Point:
def __init__(self, x, y):
self.x = x
self.y = y
point = Point(0, 5)
match point:
case Point(x=0, y=0):
print("Origin")
case Point(x=0, y=y):
print(f"On Y-axis at {y}")
case Point(x=x, y=0):
print(f"On X-axis at {x}")
case Point(x=x, y=y):
print(f"Point at ({x}, {y})")
匹配型別
def process(value):
match value:
case str():
print(f"String: {value}")
case int() | float():
print(f"Number: {value}")
case list():
print(f"List with {len(value)} items")
case dict():
print(f"Dict with {len(value)} keys")
case _:
print(f"Unknown type: {type(value)}")
process("hello") # String: hello
process(42) # Number: 42
process([1, 2, 3]) # List with 3 items
使用 as 綁定變數
data = [1, 2, 3]
match data:
case [1, *rest] as full_list:
print(f"Starts with 1, rest: {rest}, full: {full_list}")
輸出:
Starts with 1, rest: [2, 3], full: [1, 2, 3]
實際範例
解析指令
def handle_command(command):
match command.split():
case ["quit" | "exit"]:
return "Goodbye!"
case ["hello", name]:
return f"Hello, {name}!"
case ["add", *numbers]:
return f"Sum: {sum(int(n) for n in numbers)}"
case ["help"]:
return "Available commands: quit, hello <name>, add <numbers...>"
case _:
return "Unknown command"
print(handle_command("hello Alice")) # Hello, Alice!
print(handle_command("add 1 2 3 4")) # Sum: 10
print(handle_command("quit")) # Goodbye!
處理 API 回應
def handle_response(response):
match response:
case {"status": "success", "data": data}:
print(f"Success! Data: {data}")
case {"status": "error", "message": msg}:
print(f"Error: {msg}")
case {"status": status}:
print(f"Unknown status: {status}")
case _:
print("Invalid response format")
handle_response({"status": "success", "data": [1, 2, 3]})
handle_response({"status": "error", "message": "Not found"})
簡單計算機
def calculate(expression):
match expression:
case ("+", a, b):
return a + b
case ("-", a, b):
return a - b
case ("*", a, b):
return a * b
case ("/", a, b) if b != 0:
return a / b
case ("/", _, 0):
return "Error: Division by zero"
case _:
return "Invalid expression"
print(calculate(("+", 5, 3))) # 8
print(calculate(("*", 4, 7))) # 28
print(calculate(("/", 10, 0))) # Error: Division by zero