我有一个看起来有点像这样的功能。我希望函数接受io.IOBase的任何子类 - 换句话说,任何类似文件的对象。
def import_csv_file(f:io.IOBase)->pandas.DataFrame:
return pandas.read_csv(f)
当我在IntelliJ中查看对象时,类型提示的JetBrains实现拒绝任何输入,除非我提供了io.IOBase的确切实例 - 但是如果我想传入io子类的实例该怎么办。 IOBASE?有没有办法改变类型提示,说这是允许的?
答案 0 :(得分:2)
def import_csv_file(f: typing.Type[io.IOBase])->pandas.DataFrame:
return pandas.read_csv(f)
引用PEP:
有时你想谈论类对象,特别是从给定类继承的类对象。这可以拼写为Type [C],其中C是一个类。澄清:虽然C(当用作注释时)引用类C的实例,但类型[C]引用C的子类。
Python doc:
用C注释的变量可以接受类型C的值。相反,使用Type [C]注释的变量可以接受类本身的值 - 具体来说,它将接受C的类对象。例如:< / p>
a = 3 # Has type 'int'
b = int # Has type 'Type[int]'
c = type(a) # Also has type 'Type[int]'
请注意,类型[C]是协变的:
class User: ...
class BasicUser(User): ...
class ProUser(User): ...
class TeamUser(User): ...
# Accepts User, BasicUser, ProUser, TeamUser, ...
def make_new_user(user_class: Type[User]) -> User:
# ...
return user_class()
答案 1 :(得分:1)
如果使用基类(在您的情况下为io.IOBase
)注释函数参数,那么您也可以传递基类的任何子类型的实例 - 继承也适用于注释类型。
也就是说,您可以使用typing.IO
作为表示任何I / O流的泛型类型(分别用于二进制和文本I / O流的typing.TextIO
和typing.BinaryIO
)。