在运行时更改Java中的常量(做什么?!)

学习Java时,您被告知可以使用最后关键字,并且它们拥有的值(或对象引用)永远不能更改,否则,它们将不被称为常量,对吗?

几乎是真的。 实际上,您可以使用称为反射的技术来更改常数的值。 使用反射,您可以在运行时以编程方式访问和更改有关字段,方法和已加载类的构造函数的信息。

在此示例中,我们将私有常数AGE从50更改为15:

import java.lang.reflect.Field;
import java.lang.reflect.Modifier;

public class ModifyConstant {
    public static void main(String[] args) throws Exception {
        OldPerson fakeYoungPerson = new OldPerson();
        changePrivateConstant(fakeYoungPerson, "AGE", 15);
        fakeYoungPerson.sayYourAge();
    }

    public static void changePrivateConstant(Object instance, String constantName, Object newValue) throws Exception {
        // gets the Field object which represents the constant
        Field field = instance.getClass().getDeclaredField(constantName);

        // need this because AGE is 'private'
        field.setAccessible(true);

        Field modifiers = field.getClass().getDeclaredField("modifiers");

        // need this because modifiers of any Field are 'private'
        modifiers.setAccessible(true);

        // this kind of removes the 'final' keyword.
        // it actually turns off the bit representing the 'final' modifier
        modifiers.setInt(field, field.getModifiers() & ~Modifier.FINAL);

        // and now we are able to set the new value to the constant
        field.set(instance, newValue);
    }

}

class OldPerson {
    private static final Integer AGE = 50;

    public void sayYourAge() {
        System.out.println("I'm " + AGE + " yo only!");
    }
}

编译并运行此类后的结果输出为:

I'm 15 yo only!

当然,更改常数是一个完全奇怪的用例,尽管我认为这可能引起了您的注意(对吗?)。 尽管如此,反射是一项强大的技术,可帮助开发人员创建可动态配置的组件。 您还需要注意,反射会在性能方面付出很多代价,因此请明智地使用反射,并且仅在真正需要时使用。

我要说的最后一件事是,如果常量是类型,则此特定示例将不起作用串因为Java 串 Constant Pool,但这是一个不同的故事,我将在后面讲...

from: https://dev.to//claudiohigashi/changing-a-private-constant-in-java-what-33m9

发布了0 篇原创文章 · 获赞 0 · 访问量 679

猜你喜欢

转载自blog.csdn.net/cunxiedian8614/article/details/105690837