黑马程序员-JAVA基础加强-内省与注解

------- android培训java培训、期待与您交流! ---------
内省与注解
内省——IntroSpector:
     JavaBean是一种特殊的Java类,主要用于传递数据信息,这种java类中的方法主要用于访问私有的字段,且方法名符合某种命名规则。
    如果要在两个模块之间传递多个信息,可以将这些信息封装到一个JavaBean中,这种JavaBean的实例对象通常称之为值对象(Value Object,简称VO)。这些信息在类中用私有字段来存储,如果读取或设置这些字段的值,则需要通过一些相应的方法来访问,大家觉得这些方法的名称叫什么好呢?JavaBean的属性是根据其中的setter和getter方法来确定的,而不是根据其中的成员变量。如果方法名为setId,中文意思即为设置id,至于你把它存到哪个变量上,用管吗?如果方法名为getId,中文意思即为获取id,至于你从哪个变量上取,用管吗?去掉set前缀,剩余部分就是属性名,如果剩余部分的第二个字母是小写的,则把剩余部分的首字母改成小的。
    setId()的属性名 id
    isLast()的属性名 last
    setCPU的属性名是什么? CPU
    getUPS的属性名是什么? UPS

    总之,一个类被当作javaBean使用时,JavaBean的属性是根据方法名推断出来的,它根本看不到java类内部的成员变量。
应用JavaBean的好处:
    在Java EE开发中,经常要使用到JavaBean。很多环境就要求按JavaBean方式进行操作,别人都这么用和要求这么做,那你就没什么挑选的余地!
JDK中提供了对JavaBean进行操作的一些API,这套API就称为内省。如果要你自己去通过getX方法来访问私有的x,怎么做,有一定难度吧?用内省这套api操作JavaBean比用普通类的方式更方便
方法:
    PropertyDescriptor(String propertyName, Class<?> beanClass)//为符合标准的Java约定的属性构造一个存储器
    Method getReadMethod()获得应用于读取属性值得方法
    Method getWriteMethod()获得应用于写入属性值得方法
JavaBean的内省操作
package cn.itcast.day1;
import java.beans.IntrospectionException;
import java.beans.PropertyDescriptor;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
    
public class IntroSpectorTest
{
    public static void main(String[] args) throws Exception
   {
   ReflectPoint pt1 =new ReflectPoint(3,5);
   String propertyName ="x";
   //"x"-->"X"-->"getX"-->MethodGetX-->
   Object retVal = getProperty(pt1, propertyName);
   System.out.println(retVal);
   Object value =7;
   setProperty(pt1, propertyName, value);//调用设置函数
   System.out.println(pt1.getX());
}
//封装设置函数
private static void setProperty(ReflectPoint pt1, String propertyName,Object value)throws
    IntrospectionException,IllegalAccessException, InvocationTargetException 
   {
   PropertyDescriptor pd2 = new PropertyDescriptor(propertyName,pt1.getClass());建一个符合JavaBean的存储器,第一个参数为字段,第二个参数为字节码对象
   Method methodSetX=pd2.getWriteMethod();//获取带set属性字段的方法
   methodSetX.invoke(pt1,value);//用反射获取set方法的值
   }
//封装获取函数
private static Object getProperty(ReflectPoint pt1, String propertyName)throws
   IntrospectionException, IllegalAccessException,InvocationTargetException 
   {
   PropertyDescriptor pd = new PropertyDescriptor(propertyName,pt1.getClass());//建一个符合JavaBean的存储器,第一个参数为字段,第二个参数为字节码对象
   Method methodGetX=pd.getReadMethod();//获取带get属性字段的方法
   Object retVal =methodGetX.invoke(pt1);//用反射获取get方法的值
   return retVal;
   }
}
注解
   注解相当于一种标记,在程序中加了注解就等于为程序打上了某种标记,没加,则等于没有某种标记,以后,javac编译器,开发工具和其他程序可以用反射来了解你的类及各种元素上有无何种标记,看你有什么标记,就去干相应的事。标记可以加在包,类,字段,方法,方法的参数以及局部变量上。
注解的应用
    @SuppressWarnings:取消显示指定的编译器警告,比如用了过时的方法
    @Override:表示重写父类的方法,若没有,则编译器会生成一条错误的消息
    @Deprecated:为某个方法注解过时了
public class AnnotationTest
{
@SuppressWarnings("deprecation")//取消警告信息
     public static viod main(String[] args)
    { 
     System.runFinalezersOnExit(true);
    }
@Deprecated//备注方法已过时
    public static void sayHello()
    {
    System.out.println("hi,传智播客");
    }
@Override//表示重写,若没有则提示
    public boolean equals(Object obj)
    {

    }
}
注解的定义与反射调用
    注解就相当于一个你的源程序中要调用的一个类,要在源程序中应用某个注解,得先准备好了这个注解类。就像你要调用某个类,得先有开发好这个类。
注解的应用结构图
  
(自定义注解)示例代码:	
@Retention(RetentionPolicy.RUNTIME)//告诉程序说,这个注解要保存到运行时期
@Target({ElementType.METHOD,ElementType.TYPE})//告诉编译器,这个注解可以用在方法上,也可以用在类上
public @interface MyAnnotation {
	String color() default "yellow";//默认缺省值为yellow
	String value() ;//不指定
	int [] arrayAttr() default {1,2};//默认为{1,2}
	EnumTest.TrafficLamp lamp() default EnumTest.TrafficLamp.RED;//枚举类
	MetaAnnotation annotationAttr() default @MetaAnnotation("xxx");//属性中加注解,用@。可以在对别的类加注解时,改变值
}
为注解增加属性
数组类型的属性

         int [] arrayAttr() default {1,2,3};
        @MyAnnotation(arrayAttr={2,3,4})
        如果数组属性中只有一个元素,这时候属性值部分可以省略大括
枚举类型的属性
        EnumTest.TrafficLamp lamp() ;
        @MyAnnotation(lamp=EnumTest.TrafficLamp.GREEN)
注解类型的属性:
        MetaAnnotation annotationAttr() default @MetaAnnotation("xxxx");
        @MyAnnotation(annotationAttr=@MetaAnnotation(“yyy”) )
可以认为上面这个@MyAnnotation是MyAnnotaion类的一个实例对象,同样的道理,可以认为上面这个@MetaAnnotation是MetaAnnotation类的一个实例对象,调用代码如下:
        MetaAnnotation ma = myAnnotation.annotationAttr();
        System.out.println(ma.value());
package cn.itcast.day2;
import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;

import cn.itcast.day1.EnumTest;

@Retention(RetentionPolicy.RUNTIME)//Retention注释类型,是为@ItcastAnnotation注解类服务的和RetentionPolicy一起使用规定注释类保存的时间。
@Target({ElementType.METHOD,ElementType.TYPE})//注解仅作用于方法和类上
public @interface ItcastAnnotation
 {//默认为public abstract方法,给注解建立属性,因为是接口方法必须抽象	
        String color() default "blue";//不指定属性时默认为blue,属性返回值类型是String
        String value();//当只有value属性时其他属性不需要指定,调用时不需要写等号
        int[] arrayAttr() default {3,4,4};//建立int[]类型arrayAttr属性
        EnumTest.TrafficLamp lamp() default EnumTest.TrafficLamp.RED;//属性的名字叫lamp,返回值类型是枚举对象
        MetaAnnotation annotationAttr() default @MetaAnnotation("lhm");//建立MetaAnnotation注释类annotationAttr()属性方法,

}


------- android培训java培训、期待与您交流! ---------
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值