zoukankan      html  css  js  c++  java
  • Android 利用反射和 注解 进行基础类型封装

    在android开发中会遇到基础类型封装,例如数据库的model类型,Http请求的参数类型等,各种注解的应用,可以简化代码,在这里记录一下基本数据的反射和注解的基本应用。

    java自定义注解

    Java注解是附加在代码中的一些元信息,用于一些工具在编译、运行时进行解析和使用,起到说明、配置的功能。
    注解不会也不能影响代码的实际逻辑,仅仅起到辅助性的作用。包含在 java.lang.annotation 包中。

    1、元注解

    元注解是指注解的注解。包括  @Retention @Target @Document @Inherited四种。


    1.1、@Retention: 定义注解的保留策略

    @Retention(RetentionPolicy.SOURCE)   //注解仅存在于源码中,在class字节码文件中不包含
    @Retention(RetentionPolicy.CLASS)     // 默认的保留策略,注解会在class字节码文件中存在,但运行时无法获得,
    @Retention(RetentionPolicy.RUNTIME)  // 注解会在class字节码文件中存在,在运行时可以通过反射获取到
     
    2、大概代码如下
    注解类Param
    package com.ming.an;
    
    import java.lang.annotation.Documented;
    import java.lang.annotation.ElementType;
    import java.lang.annotation.Retention;
    import java.lang.annotation.RetentionPolicy;
    import java.lang.annotation.Target;
    
    @Retention(RetentionPolicy.RUNTIME) // 注解会在class字节码文件中存在,在运行时可以通过反射获取到
    @Target({ElementType.FIELD,ElementType.METHOD})//定义注解的作用目标**作用范围字段、枚举的常量/方法
    @Documented//说明该注解将被包含在javadoc中
    /**
     * 参数类
     * @author dell
     *
     */
    public @interface Param {
    	/**
    	 * 是否非空
    	 * @return
    	 */
    	boolean isNotNull() default false;
    	/**
    	 * 字段名称
    	 * @return
    	 */
    	String name() default "";
    }
    

      

    获取注解的参数等方法类

    package com.ming.an;
    
    import java.lang.reflect.Field;
    import java.lang.reflect.Method;
    import java.util.ArrayList;
    import java.util.Collections;
    import java.util.Comparator;
    import java.util.List;
    
    /**
     * 获取注解的参数等方法类
     * @author dell
     *
     */
    public class AnParam {
    	
    	@SuppressWarnings("unchecked")
    	public static List<AnParam> init(Class clazz) {
    		List<AnParam> list = new ArrayList<AnParam>();
    		/**
    		 * getClass().getGenericSuperclass()返回表示此 Class 所表示的实体(类、接口、基本类型或 void)
    		 * 的直接超类的 Type(Class<T>泛型中的类型),然后将其转换ParameterizedType。。
    		 * getActualTypeArguments()返回表示此类型实际类型参数的 Type 对象的数组。 [0]就是这个数组中第一个了。。
    		 * 简而言之就是获得超类的泛型参数的实际类型。。
    		 */
    		// clazz = clazz.getClass().getGenericSuperclass())
    		// .getActualTypeArguments()[0];
    		// FieldMeta filed = clazz.getAnnotation(FieldMeta.class);
    
    		if (clazz != null) {
    
    			/**
    			 * 返回类中所有字段,包括公共、保护、默认(包)访问和私有字段,但不包括继承的字段
    			 * clazz.getFields();只返回对象所表示的类或接口的所有可访问公共字段
    			 * 在class中getDeclared**()方法返回的都是所有访问权限的字段、方法等; 可看API
    			 * */
    			Field[] fields = clazz.getDeclaredFields();
    			//
    			for (Field f : fields) {
    				// 获取字段中包含fieldMeta的注解
    				Param meta = f.getAnnotation(Param.class);
    				if (meta != null) {
    					AnParam sf = new AnParam(meta, f);
    					list.add(sf);
    				}
    			}
    
    			// 返回对象所表示的类或接口的所有可访问公共方法
    			Method[] methods = clazz.getMethods();
    
    			for (Method m : methods) {
    				Param meta = m.getAnnotation(Param.class);
    				if (meta != null) {
    					AnParam sf = new AnParam(meta, m.getName(),
    							m.getReturnType());
    					list.add(sf);
    				}
    			}
    			// 这种方法是新建FieldSortCom类实现Comparator接口,来重写compare方法实现排序
    			// Collections.sort(list, new FieldSortCom());
    			Collections.sort(list, new Comparator<AnParam>() {
    				@Override
    				public int compare(AnParam s1, AnParam s2) {
    					// return s1.getMeta().order()-s2.getMeta().order();
    					return s1.getName().compareTo(s2.getName());// 也可以用compare来比较
    				}
    
    			});
    		}
    		return list;
    
    	}
    
    	public AnParam() {
    	}
    
    	public AnParam(Param meta, Field field) {
    		super();
    		this.meta = meta;
    		this.field = field;
    		this.name = field.getName();
    		this.type = field.getType();
    	}
    
    	public AnParam(Param meta, String name, Class<?> type) {
    		super();
    		this.meta = meta;
    		this.name = name;
    		this.type = type;
    	}
    
    	private Param meta;
    	private Field field;
    	private String name;
    	private Class<?> type;
    
    	public Param getMeta() {
    		return meta;
    	}
    
    	public void setMeta(Param meta) {
    		this.meta = meta;
    	}
    
    	public Field getField() {
    		return field;
    	}
    
    	public void setField(Field field) {
    		this.field = field;
    	}
    
    	public String getName() {
    		return name;
    	}
    
    	public void setName(String name) {
    		this.name = name;
    	}
    
    	public Class<?> getType() {
    		return type;
    	}
    
    	public void setType(Class<?> type) {
    		this.type = type;
    	}
    
    }
    

      

    以下是测试类

    package com.ming.an;
    
    public class TestParam1 {
    
    	@Param( name = "id")
    	public int id;
    	@Param(name = "name")
    	public String name;
    	@Param(name = "age")
    	public int age;
    	@Param(name = "desc", isNotNull = true)
    	public String desc;
    
    }
    
    package com.ming.an;
    
    import java.util.List;
    
    public class TestParam2 {
    
    	@Param( name = "tel")
    	public long tel;
    	@Param(name = "strs",isNotNull=true)
    	public List<String> strs;
    	@Param(name = "testParams")
    	public List<TestParam1> testParams;
    	@Param(name = "tParam", isNotNull = true)
    	public TestParam1 tParam;
    
    }
    
    
    package com.ming.an;
    
    import java.util.List;
    
    public class TestAnnotation {
    
    	public static void main(String[] args) {
    		dealWithParam(TestParam1.class);
    		dealWithParam(TestParam2.class);
    		
    		
    	}
    	
    	public static void  dealWithParam(Class clazz){
    		List<AnParam> list = AnParam.init(clazz);//获取泛型中类里面的注解
    		//输出结果
    		for(AnParam l : list){
    			System.out.println("类名:"+clazz.getName()+",字段名称:"+l.getName()+"	字段类型:"+l.getType()+
    					"	注解名称:"+l.getMeta().name()+"	注解描述:"+l.getMeta().isNotNull());
    		}
    	}
    }
    

      

     
     
     
     
     
     
     
     
     
     
     
     
     
     
     
  • 相关阅读:
    canvas粒子时钟
    数组复制
    对象拷贝
    不常见但很有用的chrome调试工具使用方法
    变形transform的副作用
    CSS页面渲染优化属性will-change
    CSS实现导航条Tab切换的三种方法
    CSS两端对齐
    CSS倒影
    CSS滤镜
  • 原文地址:https://www.cnblogs.com/xunzhi/p/5706760.html
Copyright © 2011-2022 走看看