注解学习

---------------------------------------------------------------------------------------------------------------------------

PS: 元注解: 注解的注解

 

package com.bee.springboot.util.annotation;

public interface Person {

    String name();

    int age();

    void sing();
}
package com.bee.springboot.util.annotation;

@Description(desc = "i am class annotation", author = "bee")
public class Child implements Person {

    @Override
    @Description(desc = "i am method annotation", author = "bee1")
    public String name() {
        return null;
    }

    @Override
    public int age() {
        return 0;
    }

    @Override
    public void sing() {

    }
}
package com.bee.springboot.util.annotation;


import java.lang.annotation.*;

/**
 * 声明注解
 */
//以下都是源注解
@Target({ElementType.TYPE,ElementType.METHOD})//在类和方法层面能用
@Retention(RetentionPolicy.RUNTIME)//运行时注解
@Inherited   //只会继承父类,不会实现接口
@Documented
public @interface Description {
    String desc();

    String author();

    int age() default 18;
}
package com.bee.springboot.util.annotation;

import java.lang.annotation.Annotation;
import java.lang.reflect.Method;

/**
 * 解析注解,一般操作都是在这里进行
 */
public class ParseAnn {

    public static void main(String[] args){
        //1.加载类
        try{
            Class c = Class.forName("com.bee.springboot.util.annotation.Child");
            //2.找到类上面的注解
            boolean isExist = c.isAnnotationPresent(Description.class);
            if(isExist){
                //3.拿到注解实例
                Description d = (Description) c.getAnnotation(Description.class);
                System.out.println(d.desc());
            }
            //4.找到方法上的注解
            Method[] ms = c.getMethods();
           /* for(Method m:ms){//遍历到两个方法,第二个是空指针
                boolean isMExist = m.isAnnotationPresent(Description.class);
                if(isExist){
                    Description d = m.getAnnotation(Description.class);
                    System.out.println(d.desc());
                }

            }*/

            /**************************另一种解析方法**************************************/
            //获取所有注解 进行解析
            for(Method m:ms){
                Annotation[] as = m.getAnnotations();
                for(Annotation a:as){
                    if(a instanceof Description){
                        Description d = (Description)a;
                        System.out.println(d.desc());
                    }
                }
            }

        }catch (Exception e){
            e.printStackTrace();
        }

    }
}

 --------------------------------------可以通过添加反射,获取注解上的方法,进行相关的应用-------------------------

--------------------------------------------------------------------------------------------------------------------------------

package cn.itcast.e_eg;

import cn.itcast.utils.Column;
import cn.itcast.utils.Id;
import cn.itcast.utils.Table;

// Admin=a_admin
@Table(tableName="a_admin")
public class Admin {

    @Id
    @Column(columnName = "a_id")
    private int id;
    
    @Column(columnName = "a_userName")
    private String userName;
    
    @Column(columnName = "a_pwd")
    private String pwd;
    
    public int getId() {
        return id;
    }
    public void setId(int id) {
        this.id = id;
    }
    public String getUserName() {
        return userName;
    }
    public void setUserName(String userName) {
        this.userName = userName;
    }
    public String getPwd() {
        return pwd;
    }
    public void setPwd(String pwd) {
        this.pwd = pwd;
    }
    @Override
    public String toString() {
        return "Admin [id=" + id + ", pwd=" + pwd + ", userName=" + userName
                + "]";
    }
    
}

 

package cn.itcast.e_eg;

import java.lang.reflect.Field;
import java.lang.reflect.ParameterizedType;
import java.lang.reflect.Type;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.ArrayList;
import java.util.List;

import org.apache.commons.beanutils.BeanUtils;
import org.apache.commons.dbutils.ResultSetHandler;

import cn.itcast.b_reflect.JdbcUtils;
import cn.itcast.utils.Column;
import cn.itcast.utils.Id;
import cn.itcast.utils.Table;

/**
 * 解决优化的问题:
 *       1. 当数据库表名与类名不一致、 
 *    2. 字段与属性不一样、
 *    3. 主键不叫id 
 *    
 */
public class BaseDao<T> {
    
    // 当前运行类的类型
    private Class<T> clazz;
    // 表名
    private String tableName;
    // 主键
    private String id_primary;

    // 拿到当前运行类的参数化类型中实际的类型  ( BaseDao<Admin> ,  Admin.class)
    public BaseDao(){
        Type type = this.getClass().getGenericSuperclass();
        ParameterizedType pt = (ParameterizedType) type;
        Type[] types = pt.getActualTypeArguments();
        clazz = (Class<T>) types[0];
        
        //已经拿到:  Admin.class
        
        /*******1. 获取表名*******/
        Table table = clazz.getAnnotation(Table.class);
        tableName = table.tableName();
        
        /*******2. 获取主键字段*******/
        //获取当前运行类的所有字段、遍历、获取每一个字段上的id注解
        Field[] fs = clazz.getDeclaredFields();
        for (Field f : fs) {
            
            // 设置强制访问
            f.setAccessible(true);
            
            // 获取每一个字段上的id注解
            Id anno_id = f.getAnnotation(Id.class);
            
            // 判断
            if (anno_id != null) {
                // 如果字段上有id注解,当前字段(field)是主键; 再获取字段名称
                Column column = f.getAnnotation(Column.class);
                // 主键
                id_primary = column.columnName();
                // 跳出循环
                break;
            }
        }
        
        System.out.println("表:" + tableName);
        System.out.println("主键:" + id_primary);
    }
    
    
    public T findById(int id){
        try {
            String sql = "select * from " + tableName + " where " + id_primary +"=?";
            /*
             * DbUtils的已经封装好的工具类:BeanHandler?   属性=字段
             */
            return JdbcUtils.getQuerrRunner().query(sql, new BeanHandler<T>(clazz), id);
        } catch (Exception e) {
            throw new RuntimeException(e);
        }
    }
    
    
    public List<T> getAll(){
        try {
            String sql = "select * from " + tableName;
            return JdbcUtils.getQuerrRunner().query(sql, new BeanListHandler<T>(clazz));
        } catch (Exception e) {
            throw new RuntimeException(e);
        }
    }
    
}

/**
 * 自定义结果集:封装单个Bean对象
 */
class BeanHandler<T> implements ResultSetHandler<T>{
    // 保存传入的要封装的类的字节码
    private Class<T> clazz;
    public BeanHandler(Class<T> clazz) {
        this.clazz = clazz;
    }
    
    // 封装结果集的方法
    @Override
    public T handle(ResultSet rs) throws SQLException {
        try {
            // 创建要封装的对象  ‘1’
            T t = clazz.newInstance(); 
            // 向下读一行
            if (rs.next()) {
                
                // a. 获取类的所有的Field字段数组
                Field[] fs = clazz.getDeclaredFields();
                
                // b. 遍历, 得到每一个字段类型:Field
                for (Field f : fs) {
                
                    // c. 获取”属性名称“
                    String fieldName = f.getName();
                    
                    // e. 获取Field字段上注解   【@Column(columnName = "a_userName")】
                    Column column =  f.getAnnotation(Column.class);
                    
                    // f. ”字段名“
                    String columnName = column.columnName();        // 数据库中字段 a_userName
                    
                    // g. 字段值
                    Object columnValue = rs.getObject(columnName);
                    
                    // 设置(BeanUtils组件)
                    BeanUtils.copyProperty(t, fieldName, columnValue);
                }
            }
            return t;
        } catch (Exception e) {
            throw new RuntimeException(e);
        }
    }
}


/**
 * 自定义结果集:封装多个Bean对象到List集合
 */
class BeanListHandler<T> implements ResultSetHandler<List<T>>{
    
    // 要封装的单个对象
    private Class<T> clazz;
    public BeanListHandler(Class<T> clazz){
        this.clazz = clazz;
    }

    // 把从数据库查询到的没一行记录,封装为一个对象,再提交到list集合, 返回List<T>
    @Override
    public List<T> handle(ResultSet rs) throws SQLException {
        List<T> list = new ArrayList<T>();
        try {
            // 向下读一行
            while (rs.next()) {
                
                // 创建要封装的对象  ‘1’
                T t = clazz.newInstance(); 
                
                // a. 获取类的所有的Field字段数组
                Field[] fs = clazz.getDeclaredFields();
                
                // b. 遍历, 得到每一个字段类型:Field
                for (Field f : fs) {
                
                    // c. 获取”属性名称“
                    String fieldName = f.getName();
                    
                    // e. 获取Field字段上注解   【@Column(columnName = "a_userName")】
                    Column column =  f.getAnnotation(Column.class);
                    
                    // f. ”字段名“
                    String columnName = column.columnName();        // 数据库中字段 a_userName
                    
                    // g. 字段值
                    Object columnValue = rs.getObject(columnName);
                    
                    // 设置(BeanUtils组件)
                    BeanUtils.copyProperty(t, fieldName, columnValue);
                }
                // 对象添加到集合
                list.add(t);
            }
            return list;
        } catch (Exception e) {
            throw new RuntimeException(e);
        }
    }
    
}

 

posted on 2019-01-24 10:50  biyangqiang  阅读(170)  评论(0编辑  收藏  举报

导航