Pythonic 方式与常识。类型检查
Pythonic way vs common sense. Type checking
我看到了很多问题,例如以下一个:What's the canonical way to check for type in Python?
而且总是有人回答类似这样的问题:"The pythonic way of checking types is not checking them. and here goes another passage about duck typing."
首先,我确实了解 duck typing 的优点,而且我确实经常使用它。但是不检查类型真的值得吗?
假设我有以下代码:
class DuckA:
def quack():
print("QuackA")
class DuckB:
def quack():
print("QuackB")
def duck_creator():
return DuckA()
def duck_client(duck):
duck.quack()
if __name__ is "__main__":
duck_client(DuckA()) #ok
duck_client(DuckB()) #ok
duck_client(duck_creator()) #ok
#totally fine untill you actually call it,
#which might be quite tricky to check in
#relatively big project
duck_client(duck_creator)
#one more typo, which is pretty hard to spot
#from first sight
duck_client(DuckB)
是的,我知道我们都是工程师,因此,我们支持编写足够的结构,但是各种错别字怎么办?
我是python的初学者,来自c/c++人群。基本上,所有这些涉及鸭子打字的答案对我来说有点像 "if you don't want to spend hours in debugger, you just need to write code without errors"。
那么,python 大师们,有什么 valid/pythonic/accepted 技巧可以克服这样的事情吗?
我见过各种类型检查器,它们已经足够好了,尽管我不喜欢将项目绑定到其中一个 IDE 的想法。
函数开头的断言在我看来确实很有前途。
还有其他想法吗?
我认为您正在寻找的是 Mypy,一个适用于 Python 2.7+/3.4+ 的静态类型检查器。它是 Python 3.6 的注释系统设计的类型检查器,但他们一直小心翼翼地确保它可以与旧版本的 Python 一起使用。 (事实上,类型提示的部分动机首先是 Guido 希望使用 Mypy 来帮助指导将大型代码库从 2.7 升级到 3.5。)
当然你不能在旧版本的 Python 中使用 3.6 语法。在 3.5 中,参数可以被注释,但不能是局部变量。在 3.4 中,注释是有限的。在 2.7 中,注释根本不存在。
如果你阅读文档,有几种方法可以解决这个问题,但基本思想是将所有注释放入 "public" 代码的注释中,同时编写 "typeshed" 个文件"internal" 个代码的 out-of-line 个注释。
好消息是,由于 Mypy 得到了核心语言的支持,其他静态类型检查器和相关工具,如 IDE 索引器或更深入的静态分析器,正在适应以相同的方式做事,因此,无论您用于 2.7 或 3.4 代码的是什么,都可能会与您最喜欢的 IDE 或 vim 插件或分析器或其他任何东西一起工作(如果不是今天,那么很快)。
我看到了很多问题,例如以下一个:What's the canonical way to check for type in Python?
而且总是有人回答类似这样的问题:"The pythonic way of checking types is not checking them. and here goes another passage about duck typing."
首先,我确实了解 duck typing 的优点,而且我确实经常使用它。但是不检查类型真的值得吗?
假设我有以下代码:
class DuckA:
def quack():
print("QuackA")
class DuckB:
def quack():
print("QuackB")
def duck_creator():
return DuckA()
def duck_client(duck):
duck.quack()
if __name__ is "__main__":
duck_client(DuckA()) #ok
duck_client(DuckB()) #ok
duck_client(duck_creator()) #ok
#totally fine untill you actually call it,
#which might be quite tricky to check in
#relatively big project
duck_client(duck_creator)
#one more typo, which is pretty hard to spot
#from first sight
duck_client(DuckB)
是的,我知道我们都是工程师,因此,我们支持编写足够的结构,但是各种错别字怎么办?
我是python的初学者,来自c/c++人群。基本上,所有这些涉及鸭子打字的答案对我来说有点像 "if you don't want to spend hours in debugger, you just need to write code without errors"。
那么,python 大师们,有什么 valid/pythonic/accepted 技巧可以克服这样的事情吗?
我见过各种类型检查器,它们已经足够好了,尽管我不喜欢将项目绑定到其中一个 IDE 的想法。
函数开头的断言在我看来确实很有前途。
还有其他想法吗?
我认为您正在寻找的是 Mypy,一个适用于 Python 2.7+/3.4+ 的静态类型检查器。它是 Python 3.6 的注释系统设计的类型检查器,但他们一直小心翼翼地确保它可以与旧版本的 Python 一起使用。 (事实上,类型提示的部分动机首先是 Guido 希望使用 Mypy 来帮助指导将大型代码库从 2.7 升级到 3.5。)
当然你不能在旧版本的 Python 中使用 3.6 语法。在 3.5 中,参数可以被注释,但不能是局部变量。在 3.4 中,注释是有限的。在 2.7 中,注释根本不存在。
如果你阅读文档,有几种方法可以解决这个问题,但基本思想是将所有注释放入 "public" 代码的注释中,同时编写 "typeshed" 个文件"internal" 个代码的 out-of-line 个注释。
好消息是,由于 Mypy 得到了核心语言的支持,其他静态类型检查器和相关工具,如 IDE 索引器或更深入的静态分析器,正在适应以相同的方式做事,因此,无论您用于 2.7 或 3.4 代码的是什么,都可能会与您最喜欢的 IDE 或 vim 插件或分析器或其他任何东西一起工作(如果不是今天,那么很快)。