实用 Python:EAFP VS. LBYL

发布于 2025-01-01 23:59:42 字数 2418 浏览 9 评论 0

Python 中的一个惯用手法,也是常常为那些使用异常被当成,好吧,异常的编程语言的人们所惊讶的是, EAFP : "比之请求许可,请求原谅更容易些"。简单说一下,EAFP 意味着你应该只做那些期望做的事,并且当异常从操作中抛出来的时候捕获它们,然后处理之。而人们通常使用的是 LBYL : "三思而后行"。相比 EAFP,LBYL 是你搜下检查某些事情是否会成功,然后仅当你知道它能工作的时候才继续。

如果这一切在散文层面没有任何意义,那么别担心,代码将使其显而易见。让我们考虑一个例子,接收一个可能(或者可能不会)具有某个特定键的字典。在 LBYL 中,你将在第一次使用这个键之前检查它:

  if "key" in dict_:
    value += dict_["key"]

这阻止了抛出一个 KeyError 异常的可能,这似乎是符合逻辑的。但是这个代码给用户的感觉是,异常情况时该字典拥有这个键,而不是该键可能不存在,这可能不是真的。没有注释说明一般情况,那么如果你不是这个代码的作者,那么你可能就不知道什么才是期望为真的。或者换句话说,这个代码似乎强调该键在该字典中确实有些特殊,而未必真的会出现这种情况或者有那么重要。

但如果该键一般会存在于该字典中,或者不应该被认为是任何形式的异常呢?EAFP 让你以一种不一样的方式编写同样的代码,它淡化了该键存在于该字典中的重要性:

  try:
    value += dict_["key"]
  except KeyError:
    pass

阅读这段代码,它告诉了你什么?似乎表明,该键通常会存在于该字典中,但有时候不是。如果该键缺失,那么这也不是什么大事,但如果它确实存在,那么应该用它来调用一个函数。这种将代码意味着什么清晰的传达给开发者对 Python 来说是非常重要的,因此它优于 LBYL 风格,后者可能错误的传达了该键的存在多么常见/罕见/重要。

有些人读到这里,会说相比之 LBYL,EAFP 版本更长更明显,这显然是正确的。但“显式优于隐式”这种思想是关键的 Python 自身的设计方针 ,因此,该代码的明确性是有意为之的。

除了潜在的明确性/冗长性,人们往往对 EAFP 的另一个担忧是性能。如果你是从一种触发异常是非常昂贵的编程语言来到 Python 的,那么这种担忧是可以理解的。但由于异常像 EAFP 这样用于控制流程,Python 实现努力使异常开销变小,因此编写代码时,你不应该担心异常的成本。

虽然,使用 EAFP 要提醒一下,适用于任何处理捕获异常的代码的是,不要在你的 try 中的代码之上放置过于宽泛的代码。例如,可能像这样开始写代码是很有诱惑力的:

  try:
    do_something(dict_["key"])
  except KeyError:
    pass

该代码的问题是,如果 do_something() 自身抛出了一个你不想抑制的 KeyError ,会发生什么呢?在这种情况下,你应该更明确了解你正考虑的特殊情况是什么:

  try:
    value = dict_["key"]
  except KeyError:
    pass
  else:
    do_something(value)

使用任何你有可能抑制异常的代码块,你想要尽可能多的本地化在 try 块中执行的代码。现在,如果在像 EAFP 似乎过于明确的这种情况中,你更倾向于 LBYL,那么使用 LBYL 也没有什么错误。

  if "key" in dict_:
    do_something(dict["key"])

你在本文中应该获得的关键是,EAFP 在 Python 中是一种合法的编码风格,并且当其有意义时,你应该随意使用它。

原文: Idiomatic Python: EAFP versus LBYL

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。
列表为空,暂无数据

关于作者

油焖大侠

暂无简介

文章
评论
27 人气
更多

推荐作者

5576443447

文章 0 评论 0

酒几许

文章 0 评论 0

xiaolangfanhua

文章 0 评论 0

好久不见√

文章 0 评论 0

盗心人

文章 0 评论 0

    我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
    原文