在大多数情况下,Java的最终关键字真的需要吗?



我发现一些Java ide有这样的规则,甚至在不询问用户的情况下就把事情做了。例如,简单地打开一个没有任何"final"关键字的文件,IDE就会到处插入一堆关键字,尤其是在变量上。

我的观点一直是:"如果IDE可以通过算法做到这一点,JVM也可以"

这个论点站得住脚吗?Java开发人员何时应该使用"final"关键字?每个可能是final的变量都应该这样声明吗?

谢谢!

我的观点一直是:"如果IDE可以通过算法做到这一点,jvm也可以"

这个论点站得住脚吗?

不。因为当IDE这样做时(我还没见过没有请求就默认这样做的,即使你可以显式地配置它来这样做),开发人员可以检查它是否真的是他们想要的决定。这个可以防止其他代码做违背开发人员意愿的事情。

如果在执行时只执行,那将破坏整个目的。如果我创建一个字段final是为了防止其他代码修改它,那么如果其他代码试图修改它,我希望出现编译时错误。如果它只是留给JVM,我不能依赖代码而不是来修改它。

Java开发人员何时应该使用'final'关键字?

对于字段,当该字段在构造函数中初始化且此后不更改时。

对于类,当您没有将您的类设计为子类(IMO)时。

对于方法,当您没有设计子类重写方法的代码时。

对于局部变量,您希望访问匿名内部类中的变量。(当然,您也可以将它们用于其他局部变量—我不倾向于这样做,但我知道有些人会这样做。当然,对于方法之外的代码来说,这种差异是不可见的。

你说得太模糊了,最终意味着很多事情:http://en.wikipedia.org/wiki/Final_(Java)

另外,请参阅相关讨论:https://softwareengineering.stackexchange.com/questions/115690/why-declare-final-variables-inside-methods,其中链接到以下文章:

http://www.javapractices.com/topic/TopicAction.do?Id=23

自由地使用最后一个关键字来传达你的意图。最后一个关键字有多个含义:

  • final class不能扩展
  • final方法不能被重写
  • final字段、参数和局部变量不能更改它们的

在最后一种情况下,可以理解原语的"value"在通常意义上,对象的"值"是指对象的身份,而不是状态。一旦最终对象引用的标识是固定的,它仍然可以改变它的状态,但不能改变它的身份。声明作为final的原语字段自动确保线程安全场。

有些人习惯性地将形参声明为final,因为这几乎总是期望的行为。另一些人则觉得这句话啰嗦,不太真实受益。

一致地对局部变量使用final(适当时)可以也要有用。它将注意力引向非最终的局部变量,这些变量通常有更多与之相关的逻辑例如,结果变量,累加器,循环变量)。许多找到这冗长的。一个合理的方法是使用final代替local变量中至少有一个非final局部变量方法;这有助于快速区分非最终的局部其他变量

使用final:

  • 清楚传达你的意图
  • 允许编译器和虚拟执行小优化的机器
  • 清楚地标记下列项目更简单的行为-最后说,"如果你正在寻找。复杂性,你在这里找不到。"

局部变量只能在final中使用

final修饰符可以用来防止setter方法中的滑动。

public void setLimit(int limit) {
    /*this.*/limit = limit;
}

显然是错误的;需要加入this.。在

中使用final
public void setLimit(final int limit) {
    limit = limit;
}

会导致编译错误

每个可能是final的变量都应该这样声明吗?

是的。

很多人没有意识到编译器可以做多少来帮助你避免常见的问题:

// Final parameters cannot be reassigned.  This sometimes happens accidentally
// and sometimes because people see them as convenient local variables.
publc void myFunction(final int myIntParam) {
    // Let's declare a local variable
    final String myLocalString;
    // ... there's some code here ...
    // Here, the compiler knows whether this variable has been assigned
    // The programmer knows that it has been assigned only once
    return myLocalString.toUpperCase(Locale.ENGLISH);
}

最新更新