重新初始化静态类中的最终字段

时间:2014-02-25 15:02:39

标签: java

我有一个静态类,如下所示:

public class StaticClass {

    public static final String stringValue;

    static {
        stringValue = OtherClass.someMethod();
    }

}

我们在整个地方使用StaticClass.stringValue。但是在给定的情况下,我想强制它重新加载,所以静态初始化程序再次运行。

这可能吗?

我知道我可以使用反射手动设置此字段。但实际上,这个类中有1000个字段。

我完全清楚这听起来多么奇怪,为什么我不应该这样做。我想知道这是否可行。我希望该字段是最终的,因此我的开发人员不会意外地更改值。但我希望在给定的用户输入后,所有字段都重新加载。

5 个答案:

答案 0 :(得分:1)

ClassLoader每个类只运行一次静态初始值设定项(因为类被加载到内存中)。

如果你想将静态字符串保持为final,我能看到的唯一方法就是使用自定义类加载器(或者通过ASM使用一些字节代码魔法)。

如果丢弃类加载器并使用新的类加载器再次加载类,静态块将再次运行。

请注意,这可能会导致问题,因为旧类不等于新类。引用静态最终字段的所有对象也需要重新加载。

这听起来很混乱,而且有很糟糕的设计气味。

答案 1 :(得分:0)

您可以将初始化代码重构为一个方法,该方法在静态初始化程序块中调用,并且还会在以后再次调用。

为了完整性:可以通过使用ClassLoader强制重新加载类并因此重新初始化 - 例如此tutorial。虽然技术上可行,但这不太可能是解决问题的好方法。

答案 2 :(得分:0)

如果你想要的是保持一个stringValue不能是OtherClass.someMethod()以外的关系,为什么不使用一个获取它的getter方法来代替甚至维护一个变量?

喜欢的东西:

public class StaticClass {
    public static getStringValue()
    {
        return OtherClass.someMethod();
    }
}

我认为我们需要更多关于这个问题的信息。可能有更好的方法来做你想做的事。

答案 3 :(得分:0)

简单的解决方案=删除stringValue声明之前的最后一个单词并执行此操作。

public static void staticValueInitialisation() {
            stringValue = OtherClass.someMethod();
        }

答案 4 :(得分:0)

Java有这种东西的访问修饰符。看起来你希望开发人员能够在不改变它的情况下访问该值,这就是公共(静态)getter的用途。您可以将该字段设为私有但不是最终字段,并使其他代码重新加载或执行您想要的任何其他类型的修改。