反射+自定义注解 实现(数据库语句的生成)

时间:2021-07-11 11:59:32

由于在前面写自定义注解的时候,实在不好写demo演示,当然也说了学完一些反射之后,再来写一个demo,那就趁着今天周末有空,写一个 传入Class,自动生成数据库语句的demo吧

1.首先看使用吧 

String userSql = SqlSentence.create(User.class); //数据库语句创建的调用实例
结果:create table UserTable(id integer primary key autoincrement,userName varchar(8),info text,password varchar(16))

2.看User类

public class User {

    @SqlField(length = 8)
    private String userName; //生成的数据语句是 userName varchar(8)  @SqlField
    private int password; //生成的数据语句是 password varchar(16) 因为默认长度是16  @SqlField(type = "text")
    private String info; //生成的数据语句是 info text  private int age; //没有申明@SqlField注解 不生成  private String sex; //没有申明@SqlField注解 不生成   public String getUserName() {
        return userName;
    }

    public void setUserName(String userName) {
        this.userName = userName;
    }

    public int getPassword() {
        return password;
    }

    public void setPassword(int password) {
        this.password = password;
    }

    public String getInfo() {
        return info;
    }

    public void setInfo(String info) {
        this.info = info;
    }

    public int getAge() {
        return age;
    }

    public void setAge(int age) {
        this.age = age;
    }

    public String getSex() {
        return sex;
    }

    public void setSex(String sex) {
        this.sex = sex;
    }
}

3.看自定义注解类SqlField

/**  * 配置数据库语句字段  */ @Retention(RetentionPolicy.RUNTIME)
@Target({ElementType.FIELD})
public @interface SqlField {

    /**  * 字段的类型  * @return varchar  */  String type() default "varchar";

    /**  * 字段的长度  * @return 16  */  int length() default 16;
}

4.看SqlSentence类

public class SqlSentence {

    private SqlSentence() { /* cannot be instantiated */ }

    private final static String VARCHAR = "varchar";

    /**  * @param clz class  * @return sqlite sentence  */  public static <T> String create(Class<T> clz) {
        if (clz == null) {
            return null;
        }
        try {
            Object instance = Class.forName(clz.getName()).newInstance();
            Class<?> aClass = instance.getClass();
            Field[] fields = aClass.getDeclaredFields();
            StringBuilder sb = new StringBuilder();
            for (Field field : fields) {
                field.setAccessible(true); 
                if (field.isAnnotationPresent(SqlField.class)) { //判断是否存在此注解  SqlField sqlField = field.getAnnotation(SqlField.class); //获取此注解  String fieldName = field.getName();
                    String type = sqlField.type();
                    int length = sqlField.length();
                    if (type.contains(VARCHAR)) {
                        sb.append(fieldName).append(" " + VARCHAR + "(").append(length).append("),");
                    } else { //用户自定义类型  sb.append(fieldName).append(" ").append(type).append(",");
                    }
                }
            }
            int length = sb.toString().length();
            if (length > 1) { //使用生成的字符串长度判断是否存在注解  sb = sb.deleteCharAt(sb.toString().length() - 1); //删除字符串的最后一个字符  return "create table " + clz.getSimpleName() + "Table" + "(id integer primary key autoincrement," + sb + ")";
            } else {
                throw new NullPointerException("No @SqlField annotations are configured on a field");
            }
        } catch (InstantiationException e) {
            e.printStackTrace();
        } catch (IllegalAccessException e) {
            e.printStackTrace();
        } catch (ClassNotFoundException e) {
            e.printStackTrace();
        }
        return null;
    }

}

 
 
 好了,一个简单的反射+自定义注解实现生成数据库语句的demo就ok了,如果对Android开发有所了解的人,可以看一看我在

Android系列中所写的Sqlite数据库SDK,这是一个完全运用到反射+自定义注解去写的一个小框架,当然如果在Android系列中
没有这篇文章,说明我暂时还木有更新上去。