`

利用反射实现ORM

 
阅读更多

JAVA反射机制是在运行状态中,对于任意一个类,都能够知道这个类的所有属性和方法;对于任意一个对象,都能够调用它的任意一个方法;这种动态获取的信息以及动态调用对象的方法的功能称为java语言的反射机制。 
Java反射机制主要提供了以下功能: 在运行时判断任意一个对象所属的类;在运行时构造任意一个类的对象;在运行时判断任意一个类所具有的成员变量和方法;在运行时调用任意一个对象的方法;生成动态代理。 

Java代码  收藏代码
  1. package com.royzhou.reflect;  
  2.   
  3. import java.lang.reflect.Constructor;  
  4. import java.lang.reflect.Field;  
  5. import java.lang.reflect.Method;  
  6.   
  7. public class ReflectTest {  
  8.   
  9.     private String id;  
  10.   
  11.     private String name;  
  12.   
  13.     public String property;  
  14.   
  15.     public String getId() {  
  16.         return id;  
  17.     }  
  18.   
  19.     public void setId(String id) {  
  20.         this.id = id;  
  21.     }  
  22.   
  23.     public String getName() {  
  24.         return name;  
  25.     }  
  26.   
  27.     public void setName(String name) {  
  28.         this.name = name;  
  29.     }  
  30.   
  31.     public String getProperty() {  
  32.         return property;  
  33.     }  
  34.   
  35.     public void setProperty(String property) {  
  36.         this.property = property;  
  37.     }  
  38.   
  39.     public ReflectTest() {  
  40.         System.out.println("this is a constructor with no params!!!");  
  41.     }  
  42.   
  43.     public ReflectTest(String param) {  
  44.         System.out.println("this is a constructor with  param :" + param  
  45.                 + "!!!");  
  46.     }  
  47.   
  48.     /** 
  49.      * 创建对象 
  50.      *  
  51.      * @param clazz 
  52.      * @param paramTypes:构造函数参数,如果为null表示调用无参函数 
  53.      * @return 
  54.      * @throws Exception 
  55.      */  
  56.     public Object createObject(Class clazz, Class[] paramTypes)  
  57.             throws Exception {  
  58.         Object obj = null;  
  59.         if (paramTypes == null) {  
  60.             // 无参构造函数  
  61.             obj = clazz.newInstance();  
  62.         } else {  
  63.             // 有参构造函数  
  64.             Constructor con = clazz.getConstructor(paramTypes);  
  65.             obj = con.newInstance("Test String param");  
  66.         }  
  67.         return obj;  
  68.     }  
  69.   
  70.     /** 
  71.      * 激活对象的某个方法 
  72.      *  
  73.      * @param obj 
  74.      * @param methodName 
  75.      * @throws Exception 
  76.      */  
  77.     public void invokeMethod(Object obj, String methodName) throws Exception {  
  78.         Method[] methods = obj.getClass().getDeclaredMethods(); // 拿到当前类的全部方法,包括私有的和公有的  
  79.         methods = obj.getClass().getMethods(); // 拿到当前类以及父类的所有公有方法  
  80.         for (Method m : methods) {  
  81.             if (m.getName().equals(methodName)) {  
  82.                 m.invoke(obj, new Object[] {}); // 调用方法  
  83.             }  
  84.         }  
  85.     }  
  86.   
  87.     public void getFileds(Object obj) throws Exception {  
  88.         Field[] fields = obj.getClass().getFields(); // 获取公有的属性  
  89.         fields = obj.getClass().getDeclaredFields(); // 获取公有私有属性  
  90.         for (Field f : fields) {  
  91.             System.out.println(f.getName());  
  92.         }  
  93.     }  
  94.   
  95.     public void overload(String s) {  
  96.         System.out.println("param is String :" + s);  
  97.     }  
  98.   
  99.     public void overload(int i) {  
  100.         System.out.println("param is int :" + i);  
  101.     }  
  102.   
  103.     public void testInvoke() {  
  104.         System.out.println("this is a method for invoke test!!!");  
  105.     }  
  106.       
  107.     public static void main(String[] args) throws Exception {  
  108.         ReflectTest rt = new ReflectTest();  
  109.         Object obj = rt.createObject(ReflectTest.classnull);  
  110.         System.out.println("--------------");  
  111.         obj = rt.createObject(ReflectTest.classnew Class[] { String.class });  
  112.         System.out.println("--------------");  
  113.         rt.invokeMethod(obj, "testInvoke");  
  114.         System.out.println("--------------");  
  115.         Method m = obj.getClass().getMethod("overload"int.class);  
  116.         m.invoke(obj, new Object[] { 1 });  
  117.         System.out.println("--------------");  
  118.         m = obj.getClass().getMethod("overload", String.class);  
  119.         m.invoke(obj, new Object[] { "test overload String" });  
  120.         System.out.println("--------------");  
  121.         rt.getFileds(obj);  
  122.     }  
  123. }  


利用java的反射机制可以进行简单的ORM即对象关系映射 
如下面代码: 
Java代码  收藏代码
  1. import java.lang.reflect.Method;  
  2. import java.sql.Connection;  
  3. import java.sql.PreparedStatement;  
  4. import java.sql.ResultSet;  
  5. import java.sql.ResultSetMetaData;  
  6. import java.util.ArrayList;  
  7. import java.util.List;  
  8.   
  9. public class ORMTest {  
  10.   
  11.     /** 
  12.      * @param args 
  13.      * @throws Exception 
  14.      */  
  15.     public static void main(String[] args) throws Exception {  
  16.         User user = (User) getObject(  
  17.                 "select id as Id, name as Name from user where id=1",  
  18.                 User.class);  
  19.         System.out.println(user);  
  20.     }  
  21.   
  22.     public static List<Object> getObjects(String sql, Class clazz)  
  23.             throws Exception {  
  24.         Connection conn = null;  
  25.         PreparedStatement ps = null;  
  26.         ResultSet rs = null;  
  27.         try {  
  28.             conn = JdbcUtils.getConnection();  
  29.             ps = conn.prepareStatement(sql);  
  30.             rs = ps.executeQuery();  
  31.             String[] colNames = getColNames(rs);  
  32.   
  33.             List<Object> objects = new ArrayList<Object>();  
  34.             Method[] ms = clazz.getMethods();  
  35.             while (rs.next()) {  
  36.                 Object object = clazz.newInstance(); //  
  37.                 for (int i = 0; i < colNames.length; i++) {  
  38.                     String colName = colNames[i];  
  39.                     String methodName = "set" + colName;  
  40.                     for (Method m : ms) {  
  41.                         if (methodName.equals(m.getName())) {  
  42.                             m.invoke(object, rs.getObject(colName));  
  43.                             break;  
  44.                         }  
  45.                     }  
  46.                     objects.add(object);  
  47.                 }  
  48.             }  
  49.             return objects;  
  50.         } finally {  
  51.             JdbcUtils.free(rs, ps, conn);  
  52.         }  
  53.     }  
  54.   
  55.     private static String[] getColNames(ResultSet rs) throws Exception {  
  56.         ResultSetMetaData rsmd = rs.getMetaData();  
  57.         int count = rsmd.getColumnCount();  
  58.         String[] colNames = new String[count];  
  59.         for (int i = 1; i <= count; i++) {  
  60.             colNames[i - 1] = rsmd.getColumnLabel(i);  
  61.         }  
  62.         return colNames;  
  63.     }  
  64.   
  65.     public static Object getObject(String sql, Class clazz) throws Exception {  
  66.         Connection conn = null;  
  67.         PreparedStatement ps = null;  
  68.         ResultSet rs = null;  
  69.         try {  
  70.             conn = JdbcUtils.getConnection();  
  71.             ps = conn.prepareStatement(sql);  
  72.             rs = ps.executeQuery();  
  73.             String[] colNames = getColNames(rs);  
  74.   
  75.             Object object = null;  
  76.             Method[] ms = clazz.getMethods();  
  77.             if (rs.next()) {  
  78.                 object = clazz.newInstance();  
  79.                 for (int i = 0; i < colNames.length; i++) {  
  80.                     String colName = colNames[i];  
  81.                     String methodName = "set" + colName;  
  82.                     for (Method m : ms) {  
  83.                         if (methodName.equals(m.getName())) {  
  84.                             m.invoke(object, rs.getObject(colName));  
  85.                             break;  
  86.                         }  
  87.                     }  
  88.                 }  
  89.             }  
  90.             return object;  
  91.         } finally {  
  92.             JdbcUtils.free(rs, ps, conn);  
  93.         }  
  94.     }  
  95. }  

在这个简单的ORM中,利用Java的反射机制动态创建实例,不需要事先知道要生成什么对象或对象集合,只需要在调用的时候转型(当然也可以使用jdk1.5的泛型技术),使用m.invoke(object, rs.getObject(colName))方法动态设置实例的属性,注意,在这个例子中,user类必须是一个标准的Javabean,具有各个属性的setter/getter方法以及一个没有参数的构造函数,上面例子中使用sql的别名来实现动态调用对象的方法,(Hibernate使用配置文件.hbm.xml文件完成数据库字段到javabean的映射),只需要在写查询sql的时候指定好别名就可以完成javabean属性的设置。 

假如有另外一个类 Product 
Java代码  收藏代码
  1. public class Product {  
  2.       
  3.     private String id;  
  4.       
  5.     private String name;  
  6.       
  7.     private String manufatrue;  
  8.       
  9.     public String getId() {  
  10.         return id;  
  11.     }  
  12.   
  13.     public void setId(String id) {  
  14.         this.id = id;  
  15.     }  
  16.   
  17.     public String getManufatrue() {  
  18.         return manufatrue;  
  19.     }  
  20.   
  21.     public void setManufatrue(String manufatrue) {  
  22.         this.manufatrue = manufatrue;  
  23.     }  
  24.   
  25.     public String getName() {  
  26.         return name;  
  27.     }  
  28.   
  29.     public void setName(String name) {  
  30.         this.name = name;  
  31.     }  
  32.   
  33.     public Product() {  
  34.           
  35.     }  
  36. }  

这样我们在查询的时候只需要执行下面语句就可以获得封装好的Product对象/集合 
Java代码  收藏代码
  1. Product product= (Product ) getObject("select id as Id, name as Name ,manufature as Manufature from product where id=1",Product .class);  


这样的代码更具有动态性,不用每个查询写一个查询方法 

分享到:
评论

相关推荐

    利用java反射、注解及泛型模拟ORM实现

    这篇博文“利用java反射、注解及泛型模拟ORM实现”旨在探讨如何结合这三种技术来实现对象关系映射(ORM),这是一种将数据库表与Java对象之间进行绑定的技术,简化了数据操作。 首先,我们来理解一下这三个概念: ...

    基于Java动态代理和反射机制实现ORM

    通过阅读和理解这些代码,开发者可以更直观地了解如何在实际项目中应用动态代理和反射实现ORM。 总之,基于Java动态代理和反射机制实现ORM,可以有效地解耦业务逻辑和数据库操作,提高代码的可读性和可维护性。虽然...

    反射+注解自定义ORM

    利用反射和注解,可以方便地获取到类和字段的元信息,从而动态生成对应CRUD(Create、Read、Update、Delete)操作的SQL语句。例如,通过注解`@Table`和`@Column`,可以生成`CREATE TABLE`语句;通过类实例的字段,...

    利用反射实现的持久层工具类(学习)

    本文将深入探讨如何利用反射机制来实现一个简单的持久层工具类,以供学习和参考。 反射是Java提供的一种强大的动态类型特性,它允许我们在运行时检查类的信息,包括类名、属性、方法等,并能够动态地创建对象和调用...

    .net 简单实现orm实例

    通过学习这个实例,你可以了解到ORM的基本原理,以及如何在.NET中利用反射实现数据访问层的代码。这将有助于你更好地理解和应用ORM框架,提高开发效率,减少与数据库交互的复杂性。在实际项目中,虽然简单的反射实现...

    自己实现orm框架

    ### 自己实现ORM框架 #### 一、概述 在软件开发过程中,ORM(Object-Relational Mapping,对象关系映射)是一种重要的技术手段,用于在面向对象编程语言中表示数据库记录,使程序开发者能够像使用对象一样操作...

    C#发现之旅:使用反射和特性构造自己的ORM框架实用.pdf

    在C#中,使用`typeof`或`Type.GetType`等方法可以获取到类型对象,进而利用反射API(如`GetProperties`、`GetMethod`等)获取类型的各种元数据。这些信息可以用于动态生成SQL语句,执行数据库操作,如查询、插入、...

    K-ORM 自定义ORM工具

    总的来说,K-ORM作为一款自定义的ORM工具,利用JDBC提供数据库连接和SQL执行的能力,结合Java反射机制实现对象与数据库之间的映射。它简化了数据库操作,降低了开发难度,提高了代码的可维护性。对于希望在项目中...

    反射的应用 一个简单的ORM.rar

    这个简单的ORM示例就是利用反射来获取类型的信息,进而构建SQL语句。 1. **获取类型信息**:在程序运行时,可以通过`typeof()`或`Activator.CreateInstance()`等方法获取类型信息。例如,`typeof(MyClass)`可以得到...

    C#利用反射类的技术实现sql动态增删改查.rar

    综上所述,"C#利用反射类的技术实现sql动态增删改查.rar"是一个关于如何在C#中利用反射进行数据库操作的实例,通过动态生成SQL语句,实现了对SQL数据库的灵活性和适应性。这种技术对于处理复杂的业务逻辑和多样化的...

    基于java 简易ORM 框架实现(二)

    作者可能会展开讲解如何创建DAO接口和其实现,以及如何利用JDBC(Java Database Connectivity)进行数据库操作。 接着,作者可能会讲述如何实现SQL语句的自动化生成。在ORM框架中,通常会使用动态代理或者模板方法...

    Java反射机制在数据持久层轻量级ORM框架中的应用研究.pdf

    随着ORM框架的流行,如Hibernate和MyBatis等,它们利用Java的反射机制来动态访问和操作对象属性,从而大幅减少了代码量,提高了开发效率。然而,重型的ORM框架虽然功能强大,但配置复杂,学习成本高,对小型和中型...

    自定义Dao,反射实现

    自定义Dao并通过反射实现,虽然比使用ORM框架(如Hibernate、MyBatis)更繁琐,但可以更好地控制SQL语句,避免了不必要的映射配置。这种方法适用于小型项目或对性能有较高要求的场景,同时也为学习Java反射机制提供...

    Java反射机制在数据持久层轻量级ORM框架中的应用研究.zip

    这些代理对象在执行实际方法时,会利用反射进行额外的处理,如开启事务、添加日志等。 5. **元数据获取**:ORM框架可以通过反射获取类的元数据,如类名、字段名、注解等,这些信息用于构建SQL语句、映射关系等。...

    通过类反射机制实现底层数据库连接

    通过Session,我们可以利用反射调用`save()`, `update()`, `delete()`等方法来完成数据的CRUD操作。同时,查询操作也可以通过反射完成,例如使用`createQuery()`或`createNativeQuery()`方法,它们允许我们编写HQL...

    为了高效地将Json对象转化成Java bean对象,传统上我们是在运行是利用反射来实现.zip

    总结来说,将JSON对象转化为Java Bean是Java开发中的常见操作,通常通过反射实现,但现代库如Jackson提供更高效的方法。在实际开发中,应根据项目需求选择合适的方法,兼顾易用性和性能。对于大型项目,考虑使用ORM...

    .net ORM 框架

    .NET ORM(对象关系映射)框架是...了解和掌握ORM框架能显著提升开发效率,而反射则是实现ORM功能的关键机制之一。通过学习和使用Hxj.Data,开发者可以更加轻松地进行数据库操作,并利用XML配置文件灵活调整框架行为。

    JAVA反射实现数据层框架

    4. **插件化开发**:如Spring AOP(面向切面编程)利用反射实现动态代理,可以在不修改源代码的情况下对方法进行增强。 5. **序列化与反序列化**:某些库可能会使用反射来实现对象的序列化和反序列化,如JSON转换...

    自制ORM框架源代码

    通过以上分析,我们可以看出这个自定义ORM框架的实现思路:使用注解描述对象和数据库表之间的关系,通过解析器解析这些注解信息,然后利用`JdbcUtil`类提供的数据库操作工具,以简洁的方式执行SQL语句,实现对象与...

    C# 实例 ORM

    在这个"C#实例ORM"中,我们将探讨如何在C#环境下,特别是在Visual Studio 2010或更高版本中,利用属性反射来实现数据表字段与类属性之间的映射。 首先,理解属性反射是关键。在C#中,反射是一种强大的工具,它允许...

Global site tag (gtag.js) - Google Analytics