[英]Python Structural pattern matching - pass Object to case statement
這是我的代碼
class BasePlayer:
@staticmethod
def walk(direction):
print(f"I run into {direction}")
class Archer(BasePlayer):
@staticmethod
def shoot():
print("shoot")
class Wizard(BasePlayer):
@staticmethod
def cast_spell():
print("Spell casted")
def play(expr):
match expr.split():
case [("Archer" | "Wizard") as player, "walk", ("north" | "south" | "west" | "east") as direction]:
Archer.walk(direction)
case ["Archer", "shoot"]:
Archer.shoot()
case _:
raise Exception("Command not working...")
play("Archer walk west")
到目前為止效果很好,但我希望在第一個case
語句中,我希望這樣做更通用,如下所示:
case [(Archer | Wizard) as player, "walk", ("north" | "south" | "west" | "east") as direction]:
player.walk(direction)
但是我不能在 case 語句中使用 Objects(模式不綁定 Archer)。 如果我將其保留為字符串,則player
將不是類,而只是一個字符串。
有沒有辦法使這項工作?
首先, expr
是str
類型,而expr.split()
產生一個str
list
。 您需要將 match 語句的那部分更改為一個函數,該函數將生成您想要實際匹配的類型。
您將(或可能遇到)您的通用語句版本遇到的問題的第二部分是這個特定問題,其中假定裸名是要分配的變量,因此需要解決方法(請參閱答案在該線程中了解更多詳細信息)。 故障演示如下:
>>> match some_expression:
... case [(Archer | Wizard) as player, "walk", ("north" | "south" | "west" | "east") as direction]:
... player.walk(direction)
...
File "<stdin>", line 2
SyntaxError: name capture 'Archer' makes remaining patterns unreachable
作為一個快速而骯臟的答案,我將做一件懶惰的事情並將子類作為屬性分配給一個空類(以模擬導入包含這些可播放類型的模塊,例如可播放單元的unit
模塊)。 應該做些什么來實現你想要的目標的核心思想可能是這樣的:
class unit():
"pretend this is a module"
unit.Wizard = Wizard
unit.Archer = Archer
def parse(expr):
# Parse the incoming expression to [BasePlayer, str, str, ...]
# Defaults to BasePlayer for unknown unit type.
r = expr.split()
r[0] = getattr(unit, r[0], BasePlayer)
return r
def play2(expr):
match(parse(expr)): # use the above parse function to parse the expression
case [(unit.Archer | unit.Wizard) as player, "walk", ("north" | "south" | "west" | "east") as direction]:
player.walk(direction)
case [unit.Archer as player, "shoot"]:
player.shoot()
case _:
raise Exception("Command not working...")
試用play2
功能:
>>> play2('Archer walk west')
I run into west
>>> play2('Wizard walk west')
I run into west
>>> play2('Archer shoot')
shoot
>>> play2('Wizard shoot')
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
File "<stdin>", line 8, in play2
Exception: Command not working...
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.