15

我知道Java中编译器是如何解释final关键字的,但是我们程序员应该如何解释它的含义呢?应该是:

1)这个变量不能改变(例如内部类使用)

或者

2)我不打算改变这个变量(可能对成员变量有一些优化好处)。

我之所以问,是因为我处理过默认情况下所有内容都声明为 final 的代码(上面的选项 2),在我看来,这会降低关键字的价值并隐藏真正无法改变的值!将变量声明为 final 是否还有性能优势?

4

9 回答 9

17

默认情况下一切都是最终的是一件好事。你越能对代码的不变性进行建模,它就越容易推理。

在我看来,使用final几乎与性能无关。它是关于对其余代码做出断言(没有改变这个变量),这可以帮助读者理解代码,并且可以由编译器检查。

编辑:以上是我对字段的看法。对于局部变量(包括参数),我个人只final在变量将在匿名内部类中使用时使用。这与字段不同,因为:

  • 很容易看到该方法的整个上下文 - 如果不是,这本身就是一个问题。
  • 由于它不代表对象(或类)的状态,所以不变性的好处并不真正适用。
于 2013-08-01T12:17:10.473 回答
6

final关键字应该被放弃,它应该在所有适用的情况下都是标准的,并且 finality 应该只能用一个关键字来撤销

this_variable_will_change_unexpectedly_behind_your_back

这个关键字不应该被任何 IDE 自动完成,也不应该用 Ctrl-V 插入它。

于 2013-08-01T12:31:45.190 回答
4

不久前我写了一篇关于这个的帖子。

Final帮助阅读代码:

  • 不使用 final 一切都可能是可变的(潜在的混乱)
  • 它强制在使用之前设置变量(在构造函数中很有用)

通过使用 final,您可以告诉编译器有关您的代码的一些信息,它会帮助您作为回报。

于 2013-08-01T12:21:55.270 回答
1

第二个选项是保障措施。它可以防止您意外更改或重新分配。因此,提供它很有用,当您决定要更改该变量时,您可以将其删除。

于 2013-08-01T12:16:45.513 回答
1

我不能对 Jon 已经说过的内容添加太多内容,但为了完整起见,JLS 17.5.3说 final 字段也可能导致优化;

如果在字段声明中将最终字段初始化为编译时常量表达式(第 15.28 节),则可能不会观察到最终字段的更改,因为该最终字段的使用在编译时被常量表达式的值替换.

于 2013-08-01T12:34:36.353 回答
0

我不明白你为什么认为缺乏价值。

当我看到所有最终变量时,这意味着该类是不可变的。这是一件好事,因为不可变类本质上是线程安全的。

于 2013-08-01T12:17:22.600 回答
0

一般来说,最终变量是一件好事。请注意,这仅表示该变量不能重新分配,但它指向的对象如果是可变的,则可以更改。

性能方面,final允许更积极的编译器优化

该规范允许对最终字段进行积极优化。在线程中,允许使用未在构造函数中发生的对最终字段的修改来重新排序对最终字段的读取。

于 2013-08-01T12:19:42.647 回答
0

将每个变量声明final为不会贬低final关键字。它可以帮助开发人员在调试应用程序时排除修改变量的可能性,尤其是在应用程序的多线程环境中。

随着 java 8 的发布,我们多了一个概念,叫做“ effectively final variable

从 lambda 表达式引用的局部变量必须是 final 或有效 final

如果在本地块中初始化后未修改变量,则该变量被视为有效最终变量。这意味着您现在可以在匿名类或 lambda 表达式中使用没有 final 关键字的局部变量,前提是它们必须是有效的 final。

如果您不想将有效的 final 声明为 final 变量,那么在您使用 lambda 表达式/匿名类时,此新功能会为您提供帮助。您可以避免为变量声明final关键字。effective final看看这篇文章

于 2015-11-28T13:26:11.293 回答
-1

确实使用了最终变量,因此没有人可以更改该值,它在java中作为常量工作。

让我举个例子

我创建了一个也可以被其他人使用的包,现在需要设置一些配置变量才能正确运行它。可以说它的登录包。所以可能有很少的加密选项,比如

加密方法 = HASH_ENCRYPTION

或者

加密方法 = SYMMETRIC_ENCRYPTION

我们可以定义最终变量,而不是传递整数 1、2、3,它可以帮助开发人员以更易读的形式和ofcource 我不希望用户更改它,所以我保持它是最终的,否则内部逻辑可能会中断

于 2013-08-01T12:26:59.160 回答