Python与异常
我之前是用Java的,那个时候我很喜欢系统会提醒我有异常没处理,这样我就不用去看文档了。而且如果我真的去看某个方法的文档,异常信息通常会直接在方法的说明里告诉我。
但是在Python中,我经常需要读一大段文档,才能找到一句话说会抛出什么异常。
今天我在用一个Python的第三方库,http://packages.python.org/kombu/reference/kombu.connection.html,这让我很生气。难道没有统一的文档格式吗?我在用channel方法(http://packages.python.org/kombu/reference/kombu.connection.html#kombu.connection.BrokerConnection.channel),结果文档里根本没有提到会抛出异常。我只能通过反复试错来发现这个问题。
我是不是漏掉了什么明显的东西,还是说在Python和它的文档中,异常处理只是个附带的事情?
5 个回答
Python在声明异常方面的要求和Java不一样。其实大多数编程语言都是这样的。说到Java,它经常会抛出一些没有提前声明的异常(比如NullPointerException
)。虽然在所有语言中,记录异常是比较好的习惯,但在一个连公共方法是否会被记录都无法保证的世界里,这真的算是令人惊讶吗?
看看你正在使用的库,似乎你需要创建一个Transport对象(就是那个真正引发异常的东西),它确实有一份会抛出的异常列表。真正抛出异常的是这个对象,而不是BrokerConnection。
你知道traceback
模块吗?它可能会帮助你在将来找到这些问题。
Bruce Eckel在这里详细讨论了Java的检查异常和Python的异常。关键的一句话是:
当我开始使用Python时,所有的异常都能被看到,没有一个是“消失”的。如果你想捕捉一个异常,你可以这样做,但你不需要总是写很多代码来处理这些异常。它们会传递到你想要捕捉的地方,或者如果你忘记了,它们会一直传到最外层(这样就提醒你了),但它们不会消失,这可是最糟糕的情况。我现在相信,检查异常反而让人们更容易让异常“消失”。而且,这样的代码可读性也差很多。
这篇文章值得一读。
关于文档,我想说的是,确实有些文档写得不好。
我们喜欢异常(错误)。它们是编程语言中一个很重要的特性。好的文档通常会说明在什么情况下会抛出哪些异常,个人觉得大部分文档在这方面做得不错。当然,也总有一些文档写得不好。如果你想要每个函数的异常列表,那你可能会失望。除了编写代码的程序员,没人知道这些。
读一段文字对我来说并不算太糟,尤其是那段信息通常都很重要。而且你可以用 <Ctrl+F>raises<Enter>
来快速查找...
没有标准的文档格式吗?
有的,比如Sphinx,这个工具被很多项目使用(包括 docs.python.org
,你已经知道了;还有你提到的那个项目,虽然它用的是不同的视觉风格)。当然,没人能强迫每个项目都使用它,就像你不能强迫他们使用标准的编码风格一样。但老实说,我用过的所有项目中,除了两个(PyGame和LEPL),其他的都用了Sphinx。这可能是因为我用的库比较少,得益于丰富的标准库,但还是这样。
我喜欢在没有捕获异常时被提醒
为什么呢?我猜,初学者遇到的60%的异常都是因为他们的代码写得不对,而不是因为有什么特殊的环境状态需要处理。比如 TypeError
和 ImportError
,在一个没有bug、写得好的程序中是不会出现的(除非是元编程和需要极高动态性的部分)。
总的来说,如果你希望编译器告诉你一些你之前不知道的代码信息,那你可能用错了语言。Python是动态的,你是通过测试来检查,而不是静态分析。接受这一点吧。