[英]How can I make the return-type of a function taking a sequence as input dependent on that sequences types?
我正在開發一個能夠執行 SNMP 集操作的庫。 有一個 function 具有如下簽名:
def multiset(ip: str, community: str, oids: List[str], values: List[SnmpValue]) -> List[SnmpValue]:
...
這對真實簽名略有改動,以更好地說明打字問題。 在正常操作中,function 將返回設置為相同類型列表的值。 在這個例子中看起來是多余的,但在實際代碼中有一個用例(錯誤檢測),但這會使這個打字問題有點過於復雜。
核心是我有一個function,它接受一個值序列並返回一個相同類型的序列。 這些類型僅在調用 function 的行上才真正可見。
說明這一點的另一種方法是下面的代碼示例:
from typing import Generic, TypeVar, Union, List
TSupportedTypes = Union[int, str]
T = TypeVar('T', bound=TSupportedTypes)
class Wrapper(Generic[T]):
def __init__(self, value: T) -> None:
self.value = value
def process(data: List[Wrapper[TSupportedTypes]]) -> List[TSupportedTypes]:
output = []
for item in data:
output.append(item.value)
return output
processed = process([Wrapper(1), Wrapper('foo')])
# Is it possible to make this work without an "isinstance" check?
processed[1].startswith('f')
在最后一次,類型檢查器只知道列表中的每個值要么是int
要么是str
。 在這種情況下,類型僅在調用process
時才知道。
在上述情況下,類型檢查器抱怨int
沒有屬性startswith
,但代碼仍然可以工作。
有沒有辦法告訴類型檢查器從process
function 返回的任何內容與進入它的內容相同?
目前我使用健康劑量的Any
提示,但這破壞了這段代碼中類型檢查的很大一部分,我真的很想知道這是否有效。
問題不在於process
,甚至不在於Wrapper
。 問題是列表類型被認為是同質容器類型。
List[X]
表示列表中的每個元素都是同一個 X 的一個實例。
即使您的示例的這個簡化版本也沒有類型檢查:
from typing import Union, List
TSupportedTypes = Union[int, str]
processed: List[TSupportedTypes] = [1, 'foo']
# Is it possible to make this work without an "isinstance" check?
processed[1].startswith('f')
您可以看到,對於該程序中的特定值, processed[1].startswith
是安全的,但如果您只查看類型- 這是 mypy 所做的 - 那么就無法知道這一點。 根據處理的類型processed[1]
可以是 str 或 int。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.