【问题标题】:Use python's typing library to specify more than one possible type使用 python 的类型库指定多个可能的类型
【发布时间】:2016-08-23 23:25:24
【问题描述】:

我想为一个函数指定一个类型提示,它可以接收strs 的listints 的list。有没有办法使用 Python 做到这一点?比如:

from typing import List

def my_function(list_arg: List[str|int]):

    ...
    ...

【问题讨论】:

    标签: python function data-structures type-hinting


    【解决方案1】:

    Union 正是针对这种情况而设计的。它创建一个新类型,可以是您指定的任何类型:

    from typing import Union, List
    def my_function(list_arg: Union[List[str], List[int]]) -> None: ...
    

    如果你经常使用,请给类型别名:

    MyList = Union[List[str], List[int]]
    def my_function(list_arg: MyList) -> None: ...
    

    我不建议使用@user6269244 答案建议的通用函数,除非您出于某种特定原因需要它。虽然T = TypeVar('T', int, str) 可以在简单的情况下工作,但它会更具限制性。

    例如,假设你有这样的东西:

    def apply_my_function(list_of_lists: List[MyList]) -> None:
      # each item in list_of_lists is either a List[int] or List[str]
      for arg in list_of_lists:
        my_function(arg)
    

    在这段代码中,你没有选择:你需要一个UnionList[List[T]] 不会让你同时存储一个 int 列表和一个 str 列表,因为 T 不能在 str 之间切换和int 在同一个表达式中)。

    但由于您在调用my_function 的代码中使用Union,因此您还必须在my_function 本身的签名中使用Union

    此外,泛型增加了类型的复杂性,在某些时候你会遇到类型系统的限制。因此,最好为真正需要的情况保留泛型,例如,如果您希望 my_function 的返回类型取决于参数类型:

    T = TypeVar("T", int, str)
    
    # this can't be achieved with Union:
    def my_function(list_arg: List[T]) -> T: ...
    

    【讨论】:

    • 我想这更完整,所以我将其标记为对其他人正确,但感谢@user6269244 - 它以前对我来说已经解决了这个问题!
    【解决方案2】:
    from typing import TypeVar, List
    
    T = TypeVar("T", int, str)
    
    def my_function(list_arg: List[T]):
    ...
    

    【讨论】:

    • 这实际上是正确的,但前提是需要通用函数,这从问题中并不明显。比如你想在my_function里面的变量类型或者my_function的返回类型中使用T
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2023-03-29
    • 2016-02-29
    • 1970-01-01
    • 2021-06-15
    • 2017-01-17
    • 1970-01-01
    • 2018-11-21
    相关资源
    最近更新 更多