JAVA注解 实现一个简单的sql语句生成器
2015-07-29 17:22
806 查看
注解目前非常的流行,很多主流框架都支持注解,而且自己编写代码的时候也会尽量的去用注解,一时方便,而是代码更加简洁。
注解的语法比较简单,除了@符号的使用之外,它基本与Java固有语法一致。Java SE5内置了三种标准注解:
2.@Retention(RetentionPolicy) 用于制定编译器处理策略
RetentionPolicy属性详解(jdk java.lang.annotation):
3.@Documented 用于制定文档化功能
注意使用此注解时必须设置RetentionPolicy为RUNTIME
4.@Inherited 用于指定允许继承
下面介绍一个注解具体使用实例:动态生成sql语句。
首先定义注解,表名注解@Table和列注解@Column
然后创建与数据库信息对应的Model类,在其中加入注解。
下面是用于动态生成Sql语句的方法,传入一个加入@Table和@Column注解的Model类对象。功能还不完善,读者有具体需求可自己增加更复杂的sql动态生成功能。
接着进行测试:
打印结果:
注解的语法比较简单,除了@符号的使用之外,它基本与Java固有语法一致。Java SE5内置了三种标准注解:
@Override,表示当前的方法定义将覆盖超类中的方法。 @Deprecated,使用了注解为它的元素编译器将发出警告,因为注解@Deprecated是不赞成使用的代码,被弃用的代码。 @SuppressWarnings,关闭不当编译器警告信息。
上面这三个注解多少我们都会在写代码的时候遇到。Java还提供了4中注解,专门负责新注解的创建。 1.@Target(ElementType) 用于制定限定注解的使用范围 ElementType属性详解(jdk java.lang.annotation):
public enum ElementType{ TYPE, //用于类,接口,枚举但不能是注解 FIELD, //字段上,包括枚举值 METHOD, //方法,不包括构造方法 PARAMETER, //方法的参数 CONSTRUCTOR, //构造方法 LOCAL_VARIABLE, //本地变量或catch语句 ANNOTATION_TYPE, //注解类型(无数据)PACKAGE//Java包 }
2.@Retention(RetentionPolicy) 用于制定编译器处理策略
RetentionPolicy属性详解(jdk java.lang.annotation):
publicenumRetentionPolicy{ SOURCE, //此类型会被编译器丢弃 CLASS, //此类型注解会保留在class文件中,但JVM会忽略它 RUNTIME //此类型注解会保留在class文件中,JVM会读取它 }
3.@Documented 用于制定文档化功能
注意使用此注解时必须设置RetentionPolicy为RUNTIME
4.@Inherited 用于指定允许继承
下面介绍一个注解具体使用实例:动态生成sql语句。
首先定义注解,表名注解@Table和列注解@Column
@Target({ElementType.TYPE}) //类或接口可用 @Retention(RetentionPolicy.RUNTIME) public @interface Table { String value(); //可以有多个值,一个值就必须写value,否则会报错 } @Target({ElementType.FIELD}) //类或接口可用 @Retention(RetentionPolicy.RUNTIME) public @interface Column { String value(); //一个值就必须写value }
然后创建与数据库信息对应的Model类,在其中加入注解。
@Table("User") public class User { @Column("id") private int id1; @Column("userName") private String userName1; @Column("nickname") private String nickname1; @Column("age") private int age1; @Column("city") private String city1; public int getId1() { return id1; } public void setId1(int id1) { this.id1 = id1; } public String getUserName1() { return userName1; } public void setUserName1(String userName1) { this.userName1 = userName1; } public String getNickname1() { return nickname1; } public void setNickname1(String nickname1) { this.nickname1 = nickname1; } public int getAge1() { return age1; } public void setAge1(int age1) { this.age1 = age1; } public String getCity1() { return city1; } public void setCity1(String city1) { this.city1 = city1; } } @Table("department") public class Department { @Column("id") private int id1; @Column("name") private String name1; @Column("leader") private String leader1; public int getId1() { return id1; } public void setId1(int id1) { this.id1 = id1; } public String getName1() { return name1; } public void setName1(String name1) { this.name1 = name1; } public String getLeader1() { return leader1; } public void setLeader1(String leader1) { this.leader1 = leader1; } }
下面是用于动态生成Sql语句的方法,传入一个加入@Table和@Column注解的Model类对象。功能还不完善,读者有具体需求可自己增加更复杂的sql动态生成功能。
public static String query(Object f){ StringBuilder sb = new StringBuilder(); //1.获取到class Class c = f.getClass(); //2获取到table的名字 boolean exists = c.isAnnotationPresent(Table.class); if(!exists) return null; Table t = (Table)c.getAnnotation(Table.class); String tableName = t.value(); sb.append("select * from ").append(tableName).append(" where 1=1"); //3.遍历所有的字段 Field[] fArray = c.getDeclaredFields(); for(Field field:fArray){ //4.处理每个字段对应的sql //4.1 拿到字段名 boolean fexists = field.isAnnotationPresent(Column.class); if(!fexists) continue; Column column = field.getAnnotation(Column.class); String columnName = column.value(); //4.2 拿到字段的值 通过反射 String fieldName = field.getName(); String getMethidName = "get"+fieldName.substring(0, 1).toUpperCase()+fieldName.substring(1); Object fieldValue = null; try { Method getMethod = c.getMethod(getMethidName); fieldValue = getMethod.invoke(f); } catch (Exception e) { e.printStackTrace(); } if(fieldValue == null || (fieldValue instanceof Integer && (Integer)fieldValue == 0)) continue; //4.3 拼装sql // System.out.println(fieldValue.toString()); if(fieldValue instanceof String) { if(((String) fieldValue).contains(",")){ sb.append(" and ").append(columnName).append(" in ("); String[] args =fieldValue.toString().split(","); for(String str:args){ sb.append("\'").append(str).append("\',"); } sb.deleteCharAt(sb.length()-1); //删除最后一个逗号 sb.append(")"); } else{ sb.append(" and ").append(columnName).append("=").append("\'").append(fieldValue.toString()).append("\'"); } } else if(fieldValue instanceof Integer){ sb.append(" and ").append(columnName).append("=").append(fieldValue.toString()); } } return sb.toString(); }
接着进行测试:
public static void main(String[] args) { User f1 = new User(); f1.setId1(10); User f2 = new User(); f2.setUserName1("lucy"); User f3 = new User(); f3.setCity1("shenzhen,guangzhou,zhuhai"); f3.setNickname1("wahaha"); f3.setUserName1("username"); System.out.println(query(f1)); System.out.println(query(f2)); System.out.println(query(f3)); Department d1 = new Department(); d1.setLeader1("大领导"); d1.setId1(0); Department d2 = new Department(); d2.setId1(2); System.out.println(query(d1)); System.out.println(query(d2)); }
打印结果:
select * from User where 1=1 and id=10 select * from User where 1=1 and userName='lucy' select * from User where 1=1 and userName='username' and nickname='wahaha' and city in ('shenzhen','guangzhou','zhuhai') select * from department where 1=1 and leader='大领导' select * from department where 1=1 and id=2
相关文章推荐
- java 基础知识小结
- java String.format()的问题
- java实现链表反转
- java的封箱和拆箱
- java.util
- java 存储区
- JAVA基础点汇总(一)
- myclipse web项目 eclipse中不能运行
- Selenium运行环境搭建(Java)
- JAVA的道路 1+...1000
- 004--struts.xml配置详解
- spring各版本下载地址
- ZigZag Conversion
- 【Java】日志知识总结和常用组合配置(commons-logging,log4j,slf4j,logback)
- Java基础11 对象引用
- java调用第三方webservice(需要登录验证)
- 06 JAVA 容器
- 深入浅出学Spring Data JPA
- java 判断对象是否为空
- 【持久化框架】SpringMVC+Spring4+Mybatis3集成,开发简单Web项目