上一篇了解了自定义注解的使用,不过里面的例子没有多大使用价值,这一回来个有用点的Demo。
目标:将实体bean保存到数据库
先来定义一个实体注解
import java.lang.annotation.ElementType; import java.lang.annotation.Retention; import java.lang.annotation.RetentionPolicy; import java.lang.annotation.Target; @Target(ElementType.TYPE) @Retention(RetentionPolicy.RUNTIME) public @interface Entity { String getTableName(); }
这个注解可用在类上,它有一个变量参数getTableName。
其实意义很明显,就是一个实体类对应一张数据库的表,通过Entity注解将类和数据库表名关联起来
那么,通过什么将类的参数和数据库表中的列关联起来呢?再来定义一个注解
import java.lang.annotation.ElementType; import java.lang.annotation.Retention; import java.lang.annotation.RetentionPolicy; import java.lang.annotation.Target; @Target(ElementType.FIELD) @Retention(RetentionPolicy.RUNTIME) public @interface Column { String getName(); }
有了Column注解,类里面的属性就和表中的列关联起来了。
下面来看看POJO中怎么用这两个注解:
@Entity(getTableName = "user") public class User { @Column(getName = "user_id") private String id; @Column(getName = "user_name") private String name; @Column(getName = "user_age") private int age; public String getId() { return id; } public void setId(String id) { this.id = id; } public String getName() { return name; } public void setName(String name) { this.name = name; } public int getAge() { return age; } public void setAge(int age) { this.age = age; } }
通过Entity和Column注解,就将一个实体bean和一张数据库表连接起来了。很多ORM映射就是采取这种方式实现的。
最后,来感受一下注解给我们带来的便利,来个方法见证下~~
import java.lang.reflect.Field; import java.sql.Connection; import java.sql.PreparedStatement; public class Session { public static void main(String[] args) { Session session = new Session(); System.out.println(session.getInsertSql(new User())); } //在实际项目中,你可以save(obj)方法来保存一个bean public void save(Object obj) { // get a connection //PreparedStatement pstmt = getStatement(con, obj); //pstmt.execute(); } //得到PreparedStatement public PreparedStatement getStatement(Connection con, Object obj) throws Exception { PreparedStatement pstmt = con.prepareStatement(getInsertSql(obj)); Class<?> c = obj.getClass(); Field[] fs = c.getDeclaredFields(); for (int i = 0; i < fs.length; i++) { fs[i].setAccessible(true); pstmt.setObject(i + 1, fs[i].get(obj)); } return pstmt; } //insert into tableName(ziduan1,ziduan2...) values(?,?...) public String getInsertSql(Object obj) { StringBuilder s = new StringBuilder(); s.append("insert into "); Class<?> c = obj.getClass(); String tableName = c.getSimpleName();//类名,不包含包名 User Entity entity = (Entity) c.getAnnotation(Entity.class); if (entity != null) { tableName = entity.getTableName(); } s.append(tableName).append("("); Field[] fs = c.getDeclaredFields(); for (int i = 0; i < fs.length; i++) { String fieldName = fs[i].getName(); Column column = fs[i].getAnnotation(Column.class); if (column != null) { fieldName = column.getName(); } s = i == 0 ? s.append(fieldName) : s.append(",").append(fieldName); } s.append(") values").append(getString(fs.length)); return s.toString(); } //得到(?,?,?,...?,?) private String getString(int length) { StringBuilder s = new StringBuilder(); s.append("("); for (int i = 0; i < length; i++) { s = i == 0 ? s.append("?") : s.append(",?"); } s.append(")"); return s.toString(); } }
OK,That's all!