简体   繁体   English

Java反射〜设置原始类型的内部对象值

[英]Java Reflection ~ Set Inner Object Value Of A Primitive Type

I have an object that is either type of int, short, byte or long and I need to give it a new value. 我有一个类型为int,short,byte或long的对象,我需要给它一个新值。 Would that be possible in Java ? 用Java可以做到吗? And if yes how ? 如果是的话,怎么办?

public static void set(Object obj, int value) throws Exception
{
    Class<?> c = obj.getClass();
    if (c.equals(Integer.class))
    {
        // ???
    }
}

Integer is immutable. 整数是不可变的。 You cannot set a value to an Integer instance. 您不能为Integer实例设置值。

Similarly, other wrapper classes for primitive types are also immutable. 同样,其他用于基本类型的包装器类也是不可变的。

Yes, so long as you know what primitive type you're dealing with. 是的,只要您知道要处理的原始类型。

Class clazz = Class.forName("TheClass");
Field f = clazz.getDeclaredField("ThePrimitiveField");
Object obj;
f.setBoolean(obj, true);

This will change the "ThePrimitiveField" field of obj. 这将更改obj的“ ThePrimitiveField”字段。 If you don't know the type... 如果您不知道类型...

Field f;
Object obj;
try {
    f.setBoolean(obj, true);
} catch (IllegalArgumentException ex) {
    try {
        f.setByte(obj, 16);
    } catch (IllegalArgumentException ex) {
        try {
            f.setChar(obj, 'a');
            // etc
        }
    }
}

If you know the type do this: 如果您知道类型,请执行以下操作:

public class Main 
{
    public static void main(String[] args) 
        throws NoSuchFieldException, 
               IllegalArgumentException, 
               IllegalAccessException 
    {
        Foo            fooA;
        Foo            fooB;
        final Class<?> clazz;
        final Field    field;

        fooA = new Foo();
        fooB = new Foo();
        clazz = fooA.getClass();
        field = clazz.getDeclaredField("bar");

        System.out.println(fooA.getBar());
        System.out.println(fooB.getBar());
        field.setAccessible(true);  // have to do this since bar is private
        field.set(fooA, 42);
        System.out.println(fooA.getBar());
        System.out.println(fooB.getBar());
    }
}

class Foo
{
    private int bar;

    public int getBar()
    {
        return (bar);
    }
}

If you do not know the type you can do something like this: 如果您不知道类型,可以执行以下操作:

public class Main 
{
    public static void main(String[] args) 
        throws NoSuchFieldException, 
               IllegalArgumentException, 
               IllegalAccessException 
    {
        Foo            fooA;
        Foo            fooB;
        final Class<?> clazz;
        final Class<?> type;
        final Field    field;

        fooA = new Foo();
        fooB = new Foo();
        clazz = fooA.getClass();
        field = clazz.getDeclaredField("bar");

        System.out.println(fooA.getBar());
        System.out.println(fooB.getBar());
        field.setAccessible(true);  // have to do this since bar is private        
        type = field.getType();

        if(type.equals(int.class))
        {
            field.set(fooA, 42);
        }
        else if(type.equals(byte.class))
        {
            field.set(fooA, (byte)1);
        }
        else if(type.equals(char.class))
        {
            field.set(fooA, 'A');
        }

        System.out.println(fooA.getBar());
        System.out.println(fooB.getBar());
    }
}

class Foo
{
    private char bar;

    public char getBar()
    {
        return (bar);
    }
}

And, if you want to use wrapper classes (Integer, Character, etc..) you can add this: 并且,如果要使用包装器类(整数,字符等),则可以添加以下内容:

else if(type.equals(Integer.class))
{
    field.set(fooA, new Integer(43));
}

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM