在Java中,有一种惯例,将每个变量(局部变量或类)声明为final参数(如果它们确实是final的话)。

虽然这会使代码更加冗长,但这有助于容易阅读/掌握代码,也可以防止错误,因为意图被清晰地标记出来。

你对此有何看法?


当前回答

Final显然应该用在常量上,并加强不可变性,但在方法上还有另一个重要的用途。

Effective Java在这方面有一个完整的项目(项目15),指出了意外继承的陷阱。实际上,如果您没有为继承而设计和记录您的类,那么从它继承可能会带来意想不到的问题(该项目提供了一个很好的例子)。因此,建议在不打算继承的任何类和/或方法上使用final。

That may seem draconian, but it makes sense. If you are writing a class library for use by others then you don't want them inheriting from things that weren't designed for it - you will be locking yourself into a particular implementation of the class for back compatibility. If you are coding in a team there is nothing to stop another member of the team from removing the final if they really have to. But the keyword makes them think about what they are doing, and warns them that the class they are inheriting from wasn't designed for it, so they should be extra careful.

其他回答

我将它用于方法内部和外部的常量。

我有时只将它用于方法,因为我不知道子类是否不想覆盖给定的方法(无论出于什么原因)。

至于类,我只对一些基础类使用了final类。

IntelliJ IDEA会在函数参数被写入函数内部时发出警告。我已经停止使用final作为函数参数了。我在java运行库中也没有看到它们。

为:

Final fields - Marking fields as final forces them to be set by end of construction, making that field reference immutable. This allows safe publication of fields and can avoid the need for synchronization on later reads. (Note that for an object reference, only the field reference is immutable - things that object reference refers to can still change and that affects the immutability.) Final static fields - Although I use enums now for many of the cases where I used to use static final fields.

考虑但审慎地使用:

最终类——框架/API设计是我唯一考虑的情况。 Final方法——基本上与Final类相同。如果你疯狂地使用模板方法模式,并把东西标记为final,你可能太依赖继承而不是委托。

忽略,除非感觉肛门:

Method parameters and local variables - I RARELY do this largely because I'm lazy and I find it clutters the code. I will fully admit that marking parameters and local variables that I'm not going to modify is "righter". I wish it was the default. But it isn't and I find the code more difficult to understand with finals all over. If I'm in someone else's code, I'm not going to pull them out but if I'm writing new code I won't put them in. One exception is the case where you have to mark something final so you can access it from within an anonymous inner class.

我从来没有遇到过在变量上有最后一个关键字就能阻止我犯错误的情况,所以目前我认为这是一种巨大的浪费时间。

除非有真正的理由这样做(比如你想要明确指出变量是final的),否则我宁愿不这样做,因为我发现这样做会使代码的可读性降低。

但是,如果您没有发现它会使代码更难阅读或更长时间地编写,那么无论如何都可以使用它。

编辑:作为一个澄清(并试图赢回反对票),我不是说不要将常量标记为最终值,我是说不要做这样的事情:

public String doSomething() {
  final String first = someReallyComplicatedExpressionToGetTheString();
  final String second = anotherReallyComplicatedExpressionToGetAnother();

  return first+second;
}

在我看来,这只是让代码更难阅读。

同样值得记住的是,所有final的作用都是防止你重新分配变量,它并没有使它成为不可变或类似的东西。

我很少在方法或类上使用final,因为我喜欢允许人们重写它们。

否则,我只使用finally如果它是一个公共/私有静态最终类型SOME_CONSTANT;

强烈鼓励使用final作为常量。但是,我不会将它用于方法或类(或者至少考虑一下),因为它使测试更加困难,如果不是不可能的话。如果一定要让一个类或方法成为final,请确保这个类实现了一些接口,这样就可以让一个模拟实现相同的接口。