[英]Java Reflection: Instantiate a new object with specified type
I'm newbie on reflection and I try to exercise with it... 我是反思的新手,我试着用它锻炼......
This is the code... 这是代码......
for (java.lang.reflect.Field field : fields) {
String getter = "get"+field.getName().substring(0,1).toUpperCase()+field.getName().substring(1);
String setter = "set"+field.getName().substring(0,1).toUpperCase()+field.getName().substring(1);
java.lang.reflect.Method getterMethod;
java.lang.reflect.Method setterMethod;
try {
getterMethod = this.getClass().getMethod(getter, null);
Object valueGetted = getterMethod.invoke(this, null);
Class[] paramForSetter = new Class[1];
paramForSetter[0] = valueGetted.getClass();
setterMethod = p.getClass().getMethod(setter, paramForSetter);
setterMethod.invoke(p.getClass(),XXXX);
System.out.println("");
} catch (SecurityException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (NoSuchMethodException e) {
// TODO Auto-Trace();
} catch (IllegalArgumentException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (IllegalAccessException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (InvocationTargetException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
I think that is a stupid question.. On XXXXX I want an object with the type and value of value getted... 我认为这是一个愚蠢的问题..在XXXXX上我想要一个具有值类型和值的对象...
I thought that was useful... but is not.. 我认为这很有用......但不是..
setterMethod.invoke(p.getClass(),(valueGetted.getClass().getName()) valueGetted );
Help! 救命!
The correct code should look as follows: Things to note: - need to use getDeclaredFields() - getters don't start with get for boolean fields - setter.invoke() needs to be called with the correct params - use of field.getType() while getting the setter [handles primitive types] 正确的代码应该如下所示:需要注意的事项: - 需要使用getDeclaredFields() - getters不以get for boolean fields开头 - 需要使用正确的params调用setter.invoke() - 使用field.getType ()获取setter [处理原始类型]
import java.lang.reflect.Field;
public class Main {
private static MyObject clone(MyObject p) {
final MyObject clone = new MyObject();
Field[] fields = p.getClass().getDeclaredFields();
for (java.lang.reflect.Field field : fields) {
// Boolean properties will hav eis prefix instead of get
String getter = "get" + field.getName().substring(0, 1).toUpperCase() + field.getName().substring(1);
String setter = "set" + field.getName().substring(0, 1).toUpperCase() + field.getName().substring(1);
java.lang.reflect.Method getterMethod;
java.lang.reflect.Method setterMethod;
try {
getterMethod = p.getClass().getMethod(getter, null);
Object valueGetted = getterMethod.invoke(p, null);
Class[] paramForSetter = new Class[1];
paramForSetter[0] = valueGetted.getClass();
setterMethod = p.getClass().getMethod(setter, field.getType());
setterMethod.invoke(clone, valueGetted);
System.out.println(" Successfully copied " + field.getName());
} catch (Exception ex) {
System.err.println(" Error copying " + field.getName() + ": " + ex.getMessage());
}
}
return clone;
}
public static void main(String[] args) {
MyObject m = new MyObject(1, 2L, "3", true);
System.out.println("Main.main: Original = " + m);
MyObject c = clone(m);
System.out.println("Main.main: Clone = " + c);
}
}
class MyObject {
private int myInt;
private Long myLong;
private String myString;
private Boolean myBool;
MyObject() {
}
MyObject(int myInt, Long myLong, String myString, Boolean myBool) {
this.myInt = myInt;
this.myLong = myLong;
this.myString = myString;
this.myBool = myBool;
}
public int getMyInt() {
return myInt;
}
public void setMyInt(int myInt) {
this.myInt = myInt;
}
public Long getMyLong() {
return myLong;
}
public void setMyLong(Long myLong) {
this.myLong = myLong;
}
public String getMyString() {
return myString;
}
public void setMyString(String myString) {
this.myString = myString;
}
public Boolean isMyBool() {
return myBool;
}
public void setMyBool(Boolean myBool) {
this.myBool = myBool;
}
@Override
public String toString() {
return "MyObject{" +
"myInt=" + myInt +
", myLong=" + myLong +
", myString='" + myString + '\'' +
", myBool=" + myBool +
'}';
}
}
Given a getter Method m
, 给出一个getter
Method m
,
m.getReturnType().newInstance()
will construct an instance as long as f
's type is a public
concrete type (not an interface or abstract class) with a public
zero argument constructor. 只要
f
的类型是具有public
零参数构造函数的public
具体类型(不是接口或抽象类),就会构造一个实例。 And it won't work for public, non-static inner classes. 它不适用于公共的,非静态的内部类。
It also won't work for primitive return types like Integer.TYPE
. 它也不适用于
Integer.TYPE
等原始返回类型。
So given that large set of caveats, your best bet is to write a method that looks at the return type and creates an object. 因此,考虑到大量的警告,最好的办法是编写一个查看返回类型并创建对象的方法。 That way, you can return
Collections.emptyList()
for the abstract but commonly used return type List
, and can return 0
for int
. 这样,您可以为抽象但常用的返回类型
List
返回Collections.emptyList()
,并且可以为int
返回0
。
I think it's much more simple if you want juste get and set value of a field by using methods provides by Java Reflection API rather than trying to get getters and setters method's names manually. 我认为如果你想通过使用Java Reflection API提供的方法而不是试图手动获取getter和setters方法的名称来获取juste get和设置字段值,那就简单得多了。
This type of function can be used to get a field value : 这种类型的函数可用于获取字段值:
Object getFieldValue(Field afield, Object obj){
if(!field.isAccessible()) field.setAccessible(true);
return field.get(obj);
}
You can get the value of field by using the field.set(obj,value) ... 您可以使用field.set(obj,value)获取字段的值...
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.