将final字段与其声明位置分开初始化,但不适用于Java中的最终静态字段。为什么?

时间:2011-11-16 06:22:39

标签: java

最终字段必须按照惯例在Java中初始化一次。不允许其他初始化。以下程序演示了如何在类中使用最终最终静态字段。

package main;

import java.util.ArrayList;
import java.util.List;

final public class Main
{
    private final static int a=10;
    private final List<String> list;

    public Main()
    {
        list=new ArrayList<String>();
        list.add("A");
        list.add("B");
        list.add("C");
        list.add("D");
    }

    private void show()
    {
        for(String l:list)
        {
            System.out.println(l);
        }
    }

    public static void main(String[] args)
    {
        new Main().show();
    }
}

在上面的代码中,类型list final 字段ArrayList正在构造函数本身中初始化。但是,同样的事情不适用于最终静态字段a。尝试在构造函数体中初始化a会导致编译时错误,指示“无法为最终变量a 分配值。为什么同样的事情不适用于允许在构造函数中初始化的最终静态字段列表?

3 个答案:

答案 0 :(得分:6)

同样的事情 适用于最终的静态字段 - 但是最接近的 static 等同于构造函数,即静态初始化器:

private final static int x;

static {
    x = 10;
}

(可以说它更接近实例初始化器而不是构造函数,但它是最接近静态的。它不像你可以指定参数或任何东西。)

构造函数在类的每个实例化上运行 - 如果它能够更改最终的 static 字段,那么它不会是最终的,是吗?请记住,与该类型关联的静态变量只有一个“副本”,而不是与实例变量一样与该类型的每个实例关联的一个

答案 1 :(得分:2)

如果你单独声明final是每个实例的一个常量,你可以像你一样在构造函数中初始化它。但是如果声明final static,则所有实例将共享同一个变量。因此,您无法在构造函数中初始化,因为您尝试在创建实例时更改值。

答案 2 :(得分:0)

您已经使用其定义初始化了一个,因为您将其设置为10.之后您无法在构造函数中修改它。

运行构造函数两次也会导致列表出现问题。