java DTO对象与PO对象的相互转换

2018-09-27 10:27:50

前言:

  在实际开发中往往需要DTO对象与PO对象的相互转换;

  先说说什么是VO、DTO、DO、PO对象吧,

概念:

VO(View Object):视图对象,用于展示层,它的作用是把某个指定页面(或组件)的所有数据封装起来。

DTO(Data Transfer Object):数据传输对象,这个概念来源于J2EE的设计模式,原来的目的是为了EJB的分布式应用提供粗粒度的数据实体,以减少分布式调用的次数,从而提高分布式调用的性能和降低网络负载,但在这里,我泛指用于展示层与服务层之间的数据传输对象。

DO(Domain Object):领域对象,就是从现实世界中抽象出来的有形或无形的业务实体。

PO(Persistent Object):持久化对象,它跟持久层(通常是关系型数据库)的数据结构形成一一对应的映射关系,如果持久层是关系型数据库,那么,数据表中的每个字段(或若干个)就对应PO的一个(或若干个)属性。

  下面看个例子:


PO对象Student:       

 1 /**
 2  * @author libo
 3  * @date 2018年9月20日 下午8:44:33
 4  */
 5 public class Student {
 6     
 7     private Integer id;
 8     private String name;
 9     private Integer age;
10     private String address;
11     
12     public Integer getId() {
13         return id;
14     }
15     public void setId(Integer id) {
16         this.id = id;
17     }
18     public String getName() {
19         return name;
20     }
21     public void setName(String name) {
22         this.name = name;
23     }
24     public Integer getAge() {
25         return age;
26     }
27     public void setAge(Integer age) {
28         this.age = age;
29     }
30     public String getAddress() {
31         return address;
32     }
33     public void setAddress(String address) {
34         this.address = address;
35     }
36     @Override
37     public String toString() {
38         return "Student [id=" + id + ", name=" + name + ", age=" + age + ", address=" + address + "]";
39     }
40     
41     
42 }
Student【PO类】

DTO对象StudentDTO:

 1 /**
 2  * @author libo
 3  * @date 2018年9月20日 下午8:45:56
 4  */
 5 public class StudentDTO extends Student{
 6     
 7     private Integer starAge;
 8     private Integer endAge;
 9     
10     public Integer getStarAge() {
11         return starAge;
12     }
13     public void setStarAge(Integer starAge) {
14         this.starAge = starAge;
15     }
16     public Integer getEndAge() {
17         return endAge;
18     }
19     public void setEndAge(Integer endAge) {
20         this.endAge = endAge;
21     }
22     @Override
23     public String toString() {
24         return "StudentDTO [starAge=" + starAge + ", endAge=" + endAge + "]"+super.toString();
25     }
26     
27     
28 }

 


相信这已经知道了什么是DTO、PO对象了,现在言归正传,通过反射实现相互转换。也就是共有的属性但类型不同的相互转换。赋值给相同属性名的属性中去。

上代码:这里是可以相互转换的,第一个转第二个无论是否DTO

  1 import java.lang.reflect.Field;
  2 import java.lang.reflect.Method;
  3 import java.util.Arrays;
  4 import org.junit.Test;
  5 
  6 /**
  7  * 通过反射将Po对象转DTO对象
  8  * 
  9  * @author libo
 10  * @date 2018年9月20日 下午6:40:07
 11  */
 12 public class PoToDTO {
 13 
 14     /**
 15      * 将po对象的属性值赋值给dto对象相同属性名的属性
 16      * 此方法能将第一个转第二个无论是否DTO
 17      * @param po 赋值的对象
 18      * @param dto 被赋值的对象
 19      * @return
 20      * @throws Exception
 21      */
 22     public Object poToDto(Object po, Object dto) throws Exception {
 23         Class poClass = po.getClass();
 24         Class dtoClass = dto.getClass();
 25         // 取得po对象的所有属性
 26         Field[] poFields = poClass.getDeclaredFields();
 27         //取父类的所有属性
 28         Field[] superPoFields = poClass.getSuperclass().getDeclaredFields();
 29         //合并数组
 30         poFields = (Field[]) mergeArray(poFields,superPoFields);
 31         
 32         // 遍历拼接dto的set方法字段表示
 33         for (Field f : poFields) {
 34             String fieldName = f.getName();
 35             //取得当前get,set字符串表达形式
 36             String dtoSetMethodName = "set" + firstToBig(fieldName);
 37             String poGetMethodName = "get"+firstToBig(fieldName);
 38             
 39             //System.out.println(fieldName + "=====" + dtoSetMethodName);
 40             // 取得DTO对象的set方法
 41             Method dtoSetMethod=null;
 42             try {
 43                 dtoSetMethod = dtoClass.getMethod(dtoSetMethodName, f.getType());
 44             }catch (NoSuchMethodException e) {//如果不存在此方法跳过,
 45                 continue;
 46             }
 47             //取得Po对象的get方法
 48             Method poGetMethod = poClass.getMethod(poGetMethodName, null);
 49             // 将po对象的属性值set到dto对象中去
 50             dtoSetMethod.invoke(dto, poGetMethod.invoke(po, null));
 51         }
 52         return dto;
 53 
 54     }
 55 
 56     /**
 57      * 合并数组
 58      * @param a
 59      * @param b
 60      * @return
 61      */
 62     public Object[] mergeArray(Object[] a,Object[] b) {
 63         Object[] c = Arrays.copyOf(a, a.length+b.length);
 64         System.arraycopy(b, 0, c, a.length, b.length);
 65         return c;
 66     }
 67     
 68     /**
 69      * 首字母大写
 70      * 
 71      * @param fieldName
 72      * @return
 73      */
 74     public String firstToBig(String fieldName) {
 75         if (fieldName != null && fieldName != "") {
 76             fieldName = fieldName.substring(0, 1).toUpperCase() + fieldName.substring(1);
 77         }
 78         return fieldName;
 79     }
 80 
 81     @Test
 82     public void test() {
 83         Student stu = new Student();
 84         stu.setId(1);
 85         stu.setName("李波");
 86         stu.setAge(22);
 87         stu.setAddress("郴州");
 88         
 89         StudentDTO stuDto = new StudentDTO();
 90         System.out.println("之前===="+stuDto);
 91         try {
 92             stuDto = (StudentDTO) poToDto(stu, stuDto);
 93             System.out.println("之后===="+stuDto);
 94         } catch (Exception e) {
 95             e.printStackTrace();
 96         }
 97     }
 98     
 99     @Test//测试将dto转po
100     public void test2() {
101         StudentDTO stuDTO = new StudentDTO();
102         stuDTO.setId(1);
103         stuDTO.setName("李波");
104         stuDTO.setAge(22);
105         stuDTO.setAddress("郴州");
106         
107         Student stu = new Student();
108         Student ss = stuDTO;
109         System.out.println("之前===="+stu);
110         try {
111             stu = (Student) poToDto(stuDTO, stu);
112             System.out.println("之后===="+stu);
113         } catch (Exception e) {
114             e.printStackTrace();
115         }
116     }
117 }

 

posted @ 2018-09-27 10:37  像灭霸一样看日出  阅读(9384)  评论(0编辑  收藏  举报