在很多常用的框架當(dāng)中搪泳,比如SpringMVC寨典,還有一些ORM框架亮航,都是希望把數(shù)據(jù)包成一個(gè)Model敢辩,這樣的話既直觀兰伤,又能減少錯(cuò)誤默赂,今天就給大家講解一下這些的底層實(shí)現(xiàn)原理麦射。
首先要明白Java的反射機(jī)制
要掌握java新建對象的幾種方式
然后如何通過反射獲取屬性和方法
最后如何通過反射去執(zhí)行這些方法
這些將會將代碼里一一展示
首先先新建一個(gè)普通的JavaBean蛾娶,創(chuàng)建好setter和getter
public class Person {
private String name;
private String sex;
private int age;
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getSex() {
return sex;
}
public void setSex(String sex) {
this.sex = sex;
}
public int getAge() {
return age;
}
public void setAge(int age) {
this.age = age;
}
@Override
public String toString() {
return "Person{" +
"name='" + name + '\'' +
", sex='" + sex + '\'' +
", age=" + age +
'}';
}
}
然后就是核心代碼
public class Main {
public static void main(String[]args){
Map map=new HashMap<String,Object>();
map.put("name","jack");
map.put("sex","female");
map.put("age",18);
//傳入要最終轉(zhuǎn)化的class和要轉(zhuǎn)化的map
Person person =injectBean(Person.class,map);
System.out.println(person);
}
//使用泛型
public static final <T> T injectBean(Class<T> beanClass,Map parasMap) {
T bean = null;
try {
//通過反射生成對象
bean = beanClass.newInstance();
//還可以用Class.forName生成對象
} catch (InstantiationException e) {
e.printStackTrace();
} catch (IllegalAccessException e) {
e.printStackTrace();
}
//獲取類的方法
Method[] methods = beanClass.getMethods();
int len = methods.length;
for(int i = 0; i < len; ++i) {
Method method = methods[i];
String methodName = method.getName();
//如果方法名是set開頭的且名字長度大于3的
if(methodName.startsWith("set") && methodName.length() > 3) {
//獲取方法的參數(shù)類型
Class[] types = method.getParameterTypes();
//只有一個(gè)參數(shù)的方法才繼續(xù)執(zhí)行
if(types.length == 1) {
//取字段名且讓其首字母小寫
String attrName = firstCharToLowerCase(methodName.substring(3));
//map中是否有屬性名
if(parasMap.containsKey(attrName)) {
Object value = parasMap.get(attrName);
try {
//通過反射的方式執(zhí)行bean的mothod方法,在這里相當(dāng)于執(zhí)行set方法賦值
method.invoke(bean, new Object[]{value});
} catch (IllegalAccessException e) {
e.printStackTrace();
} catch (InvocationTargetException e) {
e.printStackTrace();
}
}
}
}
}
return bean;
}
//取字段名且讓其首字母小寫
public static String firstCharToLowerCase(String substring) {
if (substring!=null&& substring.charAt(0)>='A' && substring.charAt(0)<='Z'){
char[] arr = substring.toCharArray();
arr[0] = (char)(arr[0] + 32);
return new String(arr);
}else {
return substring;
}
}
}
代碼的邏輯不難理解潜秋,主要是要掌握java的反射機(jī)制蛔琅,我們通常還會將json轉(zhuǎn)為model,有興趣的朋友可以嘗試著改寫上面的代碼來實(shí)現(xiàn)