for语句中的final关键字

时间:2010-07-28 02:28:12

标签: java

我正在阅读网络上发现的一些代码并且依赖于这些代码(java):

private List<String> values;

[...]

for (final String str : values) {
   length += context.strlen(str);
}

在for循环中声明变量final有什么好处?我认为for循环中指定的变量已经是只读的(例如,在上面的例子中不能为'str'赋值)。

THX

5 个答案:

答案 0 :(得分:5)

  

在for循环中声明变量final有什么好处?

在一小段代码中并不多,但是,如果它有助于避免在循环时更改引用。

例如:

for( String s : values ) {
     computeSomething( s );
      ... a dozen of lines here... 
     s = s.trim();// or worst s = getOtherString();
     ... another dozen of line 
     otherComputation( s );
 }

如果你不使用final,最后一行anotherComputation可能会使用与迭代中定义的值不同的值,并且可能会引入细微的错误,同时阅读维护者将试图计算的其他代码如何使用正确的值失败该方法。

对于5到15行,这很容易发现,但对于更大的代码段,相信我,要困难得多。

使用final将阻止编译时的值更改。

... 
for( final String s : values ) {
  s = new StringBuilder( s ).reverse().toString();
}

此代码在编译时失败variable s might already have been assigned

另一个优点是允许变量在匿名内部类中使用:

for( final String s : value ) {
    doSomething( new InnerClass() {
       void something() {
             s.length();// accesing s from within the inner class 
       }
    });
 }

答案 1 :(得分:2)

将循环变量声明为final是纯粹的风格:

  • 您可以保护自己不会意外地将一个语句添加到更改循环变量的循环体中。

  • 你明白其他人在阅读代码时循环变量不会在循环体中发生变化。

我个人认为这不是一件大事。但那是因为我从来没有编写过这样做的代码......没有添加大胆的评论来解释发生了什么,以及为什么我决定这样做。 (但是,如果你处于这种可恶的环境中,我可以看到这一点......)

  

我认为for循环中指定的变量已经是只读的(例如,在上面的示例中无法为'str'赋值)。

不。 for循环变量(假设它未声明为final可以在循环体中修改。

如果您想阅读详细信息,请在JLS section 14.14中描述for循环。它没有明确提到声明为final的循环变量。但总体情况是,在for语句中声明的循环变量与任何其他变量之间的唯一区别是作用域。

答案 2 :(得分:1)

我认为for循环中指定的变量已经是只读的
它不是只读的,请尝试一下。

有些人喜欢声明局部变量'final',不知道为什么。看起来就是这种情况。

在任何情况下,不要将您在网络上找到的任意代码示例视为样式模型。

答案 3 :(得分:0)

不,它不是只读的。它是一个具有循环范围的临时变量。

通过添加final关键字,您将其设为只读。

$ cat Finals.java
import java.util.List;


public class Finals {

    public static void main(String args[]){

        int ints[] = {1,2,3,4};

        for (Integer i:ints){
            i +=20;
            System.out.println(i);
        }    
    }    
}
$ javac Finals.java -cp .
$ java Finals
21
22
23
24
$ 

答案 4 :(得分:0)

在创建匿名类使用此变量的情况下,有时可能会将其声明为final。

例如:

    String[] names = {"my name"};
    for(final String name: names){
        new Object(){
            String objName = name;
        };
    }