3 回答

TA貢獻(xiàn)1824條經(jīng)驗(yàn) 獲得超6個(gè)贊
from __future__ import annotations
NameError: name 'Position' is not defined
Position
Python 3.7+: from __future__ import annotations
from __future__ import annotations
from __future__ import annotationsclass Position: def __add__(self, other: Position) -> Position: ...
import typing
Python<3.7:使用字符串
根據(jù)PEP 484
class Position: ... def __add__(self, other: 'Position') -> 'Position': ...
self
來源
正向參考
當(dāng)類型提示包含尚未定義的名稱時(shí),該定義可以表示為字符串文本,待稍后解析。
這種情況通常發(fā)生在容器類的定義上,其中定義的類發(fā)生在某些方法的簽名中。例如,以下代碼(簡單二叉樹實(shí)現(xiàn)的開始)無法工作:
class Tree: def __init__(self, left: Tree, right: Tree): self.left = left self.right = right
為了解決這一問題,我們寫道:
class Tree: def __init__(self, left: 'Tree', right: 'Tree'): self.left = left self.right = right
字符串文字應(yīng)該包含一個(gè)有效的Python表達(dá)式(即編譯(LIT,‘val’)應(yīng)該是一個(gè)有效的代碼對象),并且一旦模塊被完全加載,它應(yīng)該在沒有錯(cuò)誤的情況下進(jìn)行計(jì)算。計(jì)算它的本地和全局命名空間應(yīng)該是相同的名稱空間,其中將計(jì)算相同函數(shù)的默認(rèn)參數(shù)。
在Python4.0中,函數(shù)和變量注釋將不再在定義時(shí)計(jì)算。相反,字符串窗體將保留在相應(yīng)的 __annotations__
字典。靜態(tài)類型檢查器在行為上沒有區(qū)別,而在運(yùn)行時(shí)使用注釋的工具將不得不執(zhí)行延遲的評估。 ...
可以使用以下特殊導(dǎo)入從Python3.7開始啟用上面描述的功能:
from __future__ import annotations
你可能會(huì)被誘惑去做的事情
A.定義假人 Position
class Position(object): passclass Position(object): ...
NameError
>>> Position.__add__.__annotations__{'other': __main__.Position, 'return': __main__.Position}
>>> for k, v in Position.__add__.__annotations__.items():... print(k, 'is Position:', v is Position) return is Position: Falseother is Position: False
B.為添加注釋而進(jìn)行的猴子補(bǔ)丁程序:
class Position: ... def __add__(self, other): return self.__class__(self.x + other.x, self.y + other.y)
Position.__add__.__annotations__['return'] = PositionPosition.__add__.__annotations__['other'] = Position
>>> for k, v in Position.__add__.__annotations__.items():... print(k, 'is Position:', v is Position) return is Position: Trueother is Position: True
結(jié)語
from __future__ import annotations

TA貢獻(xiàn)1777條經(jīng)驗(yàn) 獲得超10個(gè)贊
def __add__(self, other: 'Position') -> 'Position': return Position(self.x + other.x, self.y + other.y)
from typing import TypeVarT = TypeVar('T', bound='Position')class Position: def __init__(self, x: int, y: int): self.x = x self.y = y def __add__(self, other: T) -> T: return Position(self.x + other.x, self.y + other.y)
添加回答
舉報(bào)