【问题标题】:Kotlin ignoring CheckedException leads to potential bug sourceKotlin 忽略 CheckedException 会导致潜在的错误源
【发布时间】:2021-04-02 14:16:31
【问题描述】:

如果在 Java 代码中调用以下方法,将警告 IOException,但会简单地忽略 Kotlin 中的任何警告,因为 IOException 是已检查异常。

ParcelFileDescriptor.open(file, ParcelFileDescriptor.MODE_READ_WRITE) 

Java 强制开发人员在抛出异常时采取安全措施,但在 Kotlin 中,它只是忽略了创建潜在错误源的异常。我很确定有很多类似的情况只是简单地忽略了检查的异常。

问题是如何处理这种情况?

【问题讨论】:

  • 我不确定我是否理解您的问题。您是在询问如何在 Kotlin 中处理异常吗?或者为什么 Kotlin 一开始就没有检查异常?
  • Kotlin 的密封类是一种解决与检查异常相同的问题的方法,同时避免了对检查异常的主要批评。主要问题是使用 Java 库时。

标签: java kotlin checked-exceptions


【解决方案1】:

如果方法抛出未经检查的异常,Java 不会警告你,你是如何处理这种情况的?您可以在这里做的最好的事情是检查 java doc 或调用方法的来源,看看它是否抛出任何异常。或者只是为了捕获代码中调用此方法的任何异常。

如果您问为什么 Kotlin 没有与 java 不同的检查异常,有关 exceptions 的官方 Kotlin 文档提供了他们决定放弃检查异常的解释。引用:

对小程序的检查得出的结论是,要求异常规范既可以提高开发人员的工作效率,又可以提高代码质量,但大型软件项目的经验表明了不同的结果——生产力降低,代码质量几乎没有提高。

UPD:kotlin lang 架构师关于此事的文章:https://elizarov.medium.com/kotlin-and-exceptions-8062f589d07

【讨论】:

    【解决方案2】:

    Kotlin 不会阻止您捕获任何或所有异常;它只是不像 Java 那样强制你这样做。

    所以你仍然可以做例如:

    try {
        ParcelFileDescriptor.open(file, ParcelFileDescriptor.MODE_READ_WRITE)
    } catch (x: IOException) {
        // …
    }
    

    至于您如何知道该方法可能会引发 IOException……这很棘手。如果它是 Java 方法,那么它的 JavaDoc 会指定它(您可以从 IDE 中看到)。但如果是 Kotlin,那么文档可能会说;或者如果你有源代码,你可以检查一下。但恐怕没有真正的办法知道!您所能做的就是猜测——并确保在关键点捕获所有异常。

    将所有异常都视为未经检查并非没有争议;见this long-running discussion

    在某些情况下,Java 风格的检查异常显然是不切实际的:例如,在调用 lambda 或函数引用时。 (在这种情况下,Java 本身会强制您处理或包装已检查的异常,这可能很笨拙。)  对于涵盖多个抽象层的大型程序,存在异常冒泡到毫无意义的程度的问题;通常的解决方案是异常翻译:捕获它们并重新抛出更合适的。还有一个问题是,太多糟糕的开发人员只是简单地捕获所有异常并忽略它们(或者,充其量是记录它们),而不考虑应该如何或在哪里处理它们。

    但你可能会认为放弃所有异常检查就是把婴儿和洗澡水一起扔出去……

    (我建议 Kotlin 应该进行异常推断——找出一个方法可能抛出哪些未捕获的异常,并为它们假设一个 @Throws 声明——这将解决大多数问题知道可以在任何时候抛出哪些异常,而无需捕获它们或使任何现有代码无效。  但我可能没有看到一些问题,因为虽然这似乎是一个明显的好主意对我来说,它并没有受到好评......)

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2016-08-27
      • 2011-03-28
      • 1970-01-01
      • 2017-12-09
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2020-12-21
      相关资源
      最近更新 更多