参考资料:[Python - typing 模块 —— TypeVar 泛型 - 小菠萝测试笔记 - 博客园 (cnblogs.com)](Python - typing 模块 —— TypeVar 泛型 - 小菠萝测试笔记 - 博客园 (cnblogs.com))
python是一种
动态类型
语言,运行时不需要指定变量类型同时也存在无法及时给出语法提示或类型出错等问题
def split_str(s):
strs = s.split(",")
'''
在传递s参数时,由于无法知道s类型
所以无法在编程时给出语法提示
'''
为了解决上述问题,Python3.5、3.6新增两个特性PEP 484 和PEP 526
from typing import List, ClassVar, Dict
# int 变量,默认为0
num : int = 0
# bool 变量,默认值为True
bool_var : bool = True
# 字典变量,默认为空
dict_var : Dict = {}
# 列表变量,且列表元素为 int
primes : List[int] = []
class Starship:
# 类变量,字典类型,键 - 字符串,值 - 整型
'''
ClassVar是typing模块的一个特殊类
它想静态类型检查器指示不应该在类实例设置此变量
'''
stats : ClassVar[Dict[str,int]] = {}
# 实例变量
num : int
当你传入参数与设置的参数类型不一样时,只会warning,而不会报错
# 正常的元组打包
a = 1, 2, 3
# 加上类型提示的元组打包
t: Tuple[int, ...] = (1, 2, 3)
print(t)
t = 1, 2, 3
print(t)
# py3.8+ 才有的写法
# 不加...会有warning提示
t: Tuple[int, ...] = 1, 2, 3
print(t)
t = 1, 2, 3
print(t)
# 输出结果
(1, 2, 3)
(1, 2, 3)
(1, 2, 3)
(1, 2, 3)
# 正常元组解包
message = (1, 2, 3)
a, b, c = message
print(a, b, c) # 输出 1 2 3
# 加上类型提示的元组解包
header: str
kind: int
body: Optional[List[str]]
# 不会 warning 的栗子
header, kind, body = ("str", 123, ["1", "2", "3"])
# 会提示 warning 的栗子
header, kind, body = (123, 123, ["1", "2", "3"])
# 参数 name 类型提示 str,而函数返回值类型提示也是 str
def greeting(name: str) -> str:
return 'Hello ' + name
除了第一和第二点,其他都要import typing模块进行导入
指定类型的时候用list、set、dict、tuple也是可以的,但是不能指定里面的元素类型
且List[T]、Set[T]只能传一个类型,传多个会报错
Dict[T,T]第一个参数指定键的类型,第二个参数指定值得类型
Tuple[T] 指定一个类型的时候,仅针对同一个索引下的元素类型
如果想向List[T]一样指定全部的类型,可以Tuple[T,…]
可以将复杂一点类型给个别名,这样好用一点
# 别名
vector = List[float]
var: vector = [1.1, 2.2]
# 等价写法
var: List[float] = [1.1, 2.2]
可以自定义一个新类型:
# NewType
from typing import NewType
UserId = NewType('UserId', int)
def name_by_id(user_id: UserId) -> str:
print(user_id)
UserId('user') # Fails type check
num = UserId(5) # type: int
name_by_id(42) # Fails type check
name_by_id(UserId(42)) # OK
print(type(UserId(5)))
# 输出结果
42
42
<class 'int'>
# UserId不等于int类型,编译器检查会Warning
# 使用 UserId 类型做算术运算,得到的是 int 类型数据
内置函数,返回一个变量是否可以回调
或者typing库函数
from typing import Callable
def f():
return 1
print(callable(f))
print(isinstance(f, Callable))
# True
# True
# 语法
Callable type; Callable[[int], str] is a function of (int) -> str.
#
第一个类型[int]代表参数类型
第二个类型[str]代表返回值类型
from typing import Callable
def print_name(name: str):
print(name)
# Callable 作为函数参数使用,其实只是做一个类型检查的作用,检查传入的参数值 get_func 是否为可调用对象
# Callable 作为函数返回值使用,其实只是做一个类型检查的作用,看看返回值是否为可调用对象
def get_name(get_func: Callable[[str], None]):
return get_func
vars = get_name(print_name)
vars("test")
from typing import TypeVar
# 设置T为任意类型
T = TypeVar('T')
# 设置可以是int类型也可以是str类型
AA = TypeVar('AA',int, str)
from typing import Any
def foo(item: Any) -> int:
# Typechecks; 'item' 可以是任意类型
print(item)
return
# 隐式使用 Any
def legacy_parser(text):
...
return data
联合类型
Union[int,str] 表示既可以是int,也可以是str
from typing import Union
var : Union[int,str]
# union 嵌套 union 会自动解包
Union[Union[int, str], float] == Union[int, str, float]
可选类型
def foo_func(arg: Optional[int] = None):
print(arg)
foo_func()
foo_func(1)
# 输出结果
None
1