为啥 Kotlin 不需要明确地 try 和 catch

Posted

技术标签:

【中文标题】为啥 Kotlin 不需要明确地 try 和 catch【英文标题】:Why doesn't Kotlin require try and catch explicitly为什么 Kotlin 不需要明确地 try 和 catch 【发布时间】:2017-12-09 22:19:21 【问题描述】:

例如:

FileOutputStream("file") 

会在 Kotlin 中编译,但在 Java 中会出现编译器错误。为什么?

【问题讨论】:

kotlinlang.org/docs/reference/… Kotlin 没有检查异常,就像在 C# 和其他语言中一样 Kotlin 创造者的目标是让流行语言。所以他们添加了一堆语法糖,牺牲了一切可能让初学者感到困惑的东西。并且检查异常经常让初学者烦恼这就是为什么。 Kotlin 尽量摆脱样板代码 【参考方案1】:

Kotlin 取消了 Java 的检查异常。在编译时检查并在方法签名中声明的异常,尽管 Java 开发人员熟悉,但被广泛认为是失败的实验 outside,在某种程度上 inside Java 社区。​​p>

所以 Kotlin 取消了它们,并使用 Java 7 的 try-with-resources 的 .use 方法简写使用资源(如 FileOutputStream)相关的一些样板。

【讨论】:

如果我不知道它们会提前发生,那么处理这些异常的适当方法是什么? 对于 Kotlin 中使用的 Java 类,您可以简单地检查接口方法签名或 Javadoc。可能有一些您想要从中恢复的异常以及您想要让您的线程终止的其他异常。如上所述,FileOutputStream(File("path")).use ... 很可能是您要查找的内容。 @NateVaughan 如果它是 Kotlin 接口,则不会声明任何异常。如果没有 Javadoc 或者它不完整怎么办? @NateVaughan 如果我不知道我能得到哪些,我应该如何从他们那里恢复?这就是所谓的 Pokemon 异常处理 (catch-em-all)。抓住任何非常有帮助的对用户说出了点问题,但我不知道是什么?这正是 Kotlin 中异常的问题。 @NateVaughan 即使从Exception 中辨别出IOException 也有帮助,这里没有“周到、详细”的内容。并且由于库作者在编写文档时也没有任何编译器帮助的简单原因,文档中可能会丢失异常。另外我不明白为什么这应该只发生在您无法控制的代码中。在我自己的代码中,我经常忘记哪些方法可以抛出哪些异常,我宁愿让编译器告诉我,也不愿在 cmets 中手动编写所有这些东西(你也可以忘记检查)。【参考方案2】:

如果不让一些意见干扰,可能很难回答。我只想说 Kotlin 是针对大型软件项目的,并为您提供 Kotlin 团队声称的关于检查异常的内容(来自 https://kotlinlang.org/docs/reference/exceptions.html):

检查异常

Kotlin 没有检查异常。有很多原因 这个,但我们将提供一个简单的例子。

以下是JDK实现的示例接口 StringBuilder 类:

Appendable append(CharSequence csq) 抛出 IOException;这是做什么的 签名说?它说每次我将字符串附加到某些东西时 (StringBuilder、某种日志、控制台等)我必须赶上 那些 IOExceptions。为什么?因为它可能正在执行 IO (Writer 也实现了 Appendable)... 所以导致这种代码都是 在这个地方:

try 
    log.append(message)

catch (IOException e) 
    // Must be safe

这不好,参见Effective Java,第 65 条:不要忽视 例外。

布鲁斯·埃克尔在Does Java need Checked Exceptions? 中说:

对小程序的检查得出的结论是,需要 异常规范既可以提高开发人员的生产力,又可以 提高代码质量,但有大型软件项目的经验 暗示了一个不同的结果——生产力下降,很少或没有 提高代码质量。

其他此类引用:

Java's checked exceptions were a mistake(罗德·瓦尔德霍夫)

The Trouble with Checked Exceptions(安德斯·海尔斯伯格)

【讨论】:

以上是关于为啥 Kotlin 不需要明确地 try 和 catch的主要内容,如果未能解决你的问题,请参考以下文章

深入kotlin- 基础语法

深入kotlin- 基础语法

Kotlin 的 Iterable 和 Sequence 看起来完全一样。为啥需要两种类型?

为啥 kotlin multiplatform 不执行和导出 iOS 框架?

发现不一样的Kotlin多方位处理协程的异常

发现不一样的Kotlin多方位处理协程的异常