将一种对象类型转换为另外一种类型的常用场景
场景如下:一般后端是使用 MVC 三层架构进行分层。实体类 (User) 用于接收数据库中的数据;表现层 (UserVo) 将数据传给前端。这中间免不了要将实体类转换为表现层中的对象。即:将 User 类转换为 UserVo。
代码如下:
实体类 User:
public class User {
private String name;
private Integer age;
private String address;
getter()/setter()
...
}
UserVo:
public class User {
private String name;
private Integer age;
private String address;
getter()/setter()
...
}
将 User 转换为 UserVo:
public class TransformObject {
public UserVo createUserVoFromUser(User user) {
UserVo userVo = new UserVo();
userVo.setName(user.getName());
userVo.setAge(user.getAge());
userVo.setAddress(user.getAddress());
return userVo;
}
}
测试类 Test:
public class Test {
public static void main(String[] args) throws Exception{
TransformObject transformObject = new TransformObject();
User user = new User("zzc", 23, "北京朝阳");
UserVo userVo = transformObject.createUserVoFromUser(user);
System.out.println(userVo);
}
}
结果,显然易见。
但是,一般情况下,你的项目比较庞大,包含很多实体类的。也就是说:需要将很多实体类都转换为表现层中的类。难道你每次都要重复写这样的代码吗?
如果是这样的话,那么,整个项目的代码量非常庞大,而且难以维护。所以,这里我使用“反射”来避免这种情况(DRY:do not repeat yourself 不要重复你自己)
代码如下:
public class ReflectUtil {
public static <T> T convertObject(Object oldObj, Class<T> newClass) throws Exception{
if (null == oldObj) {
throw new RuntimeException("对象不能为空!");
}
Class<?> oldClass = oldObj.getClass();
Field[] oldFields = oldClass.getDeclaredFields();
Map<String, Object> map = new HashMap<>(16);
for (Field oldField : oldFields) {
String fieldName = oldField.getName();
String strGet = "get" + fieldName.substring(0 , 1).toUpperCase() + fieldName.substring(1);
Method method = oldClass.getMethod(strGet);
Object o = method.invoke(oldObj);
map.put(fieldName, o == null ? "" : o);
}
T newObj = newClass.newInstance();
Field[] newFields = newClass.getDeclaredFields();
for (Field newField : newFields) {
newField.setAccessible(true);
Class<?> fieldType = newField.getType();
String fieldName = newField.getName();
String fieldValue = map.get(fieldName) == null ? null : map.get(fieldName).toString();
if (null != fieldValue) {
if (String.class.equals(fieldType)) {
newField.set(newObj, fieldValue);
} else if (Integer.class.equals(fieldType)) {
newField.set(newObj, Integer.valueOf(fieldValue));
} else if (double.class.equals(fieldType)) {
newField.set(newObj, Double.parseDouble(fieldValue));
}
}
}
return newObj;
}
}
上面代码的主要逻辑:将原来对象的属性值存放在 map 中,再在遍历新对象的属性时,通过属性名从 map 中获取属性值,然后通过调用 setter() 方法给新对象进行属性赋值。
注意:
- boolean 类型的属性的 getter() 方法是以“is”开头的,并不是“get”开头。如 private boolean exist。则,它的 get() 方法就是 isExist()
- 上面只给出了部分属性的类型。还有其它类型。如:long、byte 等等。
测试:
public class Test {
public static void main(String[] args) throws Exception{
User user = new User("zzc", 23, "北京朝阳");
UserVo userVo = ReflectUtil.convertObject(user, UserVo.class);
System.out.println(userVo);
}
}
嘻嘻,这也算是反射的一种用法吧~~
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)