1、JavaBean的复杂操作;
采用遍历BeanInfo的所有属性方法来查找和设置某个类的对象的某个属性。在程序中把一个类当做JavaBean来看,就是调用
introSpector.getBeanInfo方法,得到的BeanInfo对象封装了把这个类当做JavaBean看的结果信息;
BeanInfo beaninfo=Introspector.getBeanInfo(st1.getClass());//把str1对象的类当做JavaBean来看;
PropertyDescriptor [] pds=beaninfo.getPropertyDescriptors();//得到所有的属性;
Object retVal=null;
for(PropertyDescriptor pd:pds){// 迭代获得各个属性;
if(pd.getName().equals(propertyName)){//如果得到的属性名等于配置中的propertyName的值;
Method methodGetName=pd.getReadmethod();取得该属性的方法
retVal=methodGetName.invoke();调用方法
break;
}
}
2、BeanUtils工具包操作JavaBean
配置beanutilsjar包和日志包;
System.out.println(BeanUtils.getProperty(st1,"name"));//得到name属性方法的值;
BeanUtils.setProperTy(st1,"name","chenkaidi");//设置name属性中的值;
Map转化成JavaBean以及反之;
用JavaBean来设置Map对象:
Map mao={name:"chenkai",age:"21"};
BeanUtils.setProperty(map,"name","chenchen");
BeanUtils.setProperTy(st1,"name","chenkaidi");//设置name属性中的值;以字符窜形式操作
操作结果和以下相同:
PropertyUtils.setProperty(st1,"name","chenchen");按属性类型操作;
3、注解:
deprecated过时、
@Override;
注解类:@interface A;
应用了注解的类:
@A
Class b{}
@Retention元注解,其三种取值:RetentionPolicy.SOURCE;RetentionPolicy.CLASS;RetentionPolicy·.RUNTME1;
分别对应java源文件--class文件--内存中的字节码;
@Target()定义放在类上还是Method上
注解增加属性
数组类型的属性:
int [] arrayAttr() default{1,2,3};
@MyAnnotation(arrayAttr={2,3,4})
如果数组属性中只有一个元素,这时候属性部分值可以去掉大括号。
枚举类型的属性;
EnumTest .TrafficLamp lamp();
@MyAnnotation(lamp=EnumTest.TrafficLamp.Green)
注释类型的属性:
MetaAnnotation annotationAtrr() default@M而他Annotation("XXXXX");
@MyAnnotation(annotationArrt=@MetaAnnotation("yyyy"))
可以认为上面这个@MetaAnnotation是MetaAnnotation类的一个实例对象,调用代码如下:
MetaAnnotation ma=MyAnnotation.annotationArrt();
System.out.ptint(ma.Value());
4.泛型
泛型对集合额使用;在没有使用反省是,我们可以往集合中放入任意类型的元素。当使用了泛型是,就指定了放入元素必须是
同一个类型,这样更加安全,并且当药获取对象时,不用再用强制类型转化了。
泛型的内部原理和更深的应用
泛型是是提供个javac编译器使用的。当编译器处理完后,就会去掉前面的泛型方法指定的类型
利用反射来跳过编译器;
ArrayList<Integer>collection3 =new ArrayList<Integer>();//定义一个集合
collection.add("abc");//此时由于传递的是String类型的元素,编译器在编译时会进行报错。
collection3.getClass().GetMethod("add",Object.class).invoke(collection3 , "abc");
参数化类型与原始类型的兼容性
参数化类型不考虑参数的继承关系
在创建数组实例时,数组的元素不能使用参数化的类型。
泛型的通配符?
通配符?的扩展
泛型集合的综合;
Map中有key和value。这两种元素又组合成Entry。
HashMap<String,Integer> maps= HashMap<String , Integer>();
maps.put();
maps.put();
maps.put();
然后把map变成Set//应为迭代必须实现Iterable接口
Set<Map.Entry<String ,Integer>> entrySet=maps.entrySet();
for(Map.Entry<String, Ineger> entry: entrySet){
entry.getKey;
entry.getValue;
}
自定义泛型类型应用:方法上的泛型
java中的泛型类似于c++中的模板。
只有引用类型才能作为泛型方法是我实际参数、例如以下代码:
swap(new int[]{1,2,4,3},3,4);//报错。因为int类型是基本数据类型
sawp(new String[]{"a","c","b"},2,3);//
public<T> void swap(T[] a,int i,intj){//创建一个方法改变数组里面两个元素位子
T temp=a[i];
a[i]=a[j];
a[j]=temp;
}
类上的泛型
如果类的实例对象中多处要用到一个泛型参数,既这些地方的泛型类型要保持同一个实际类型时,这时候可以采用泛型类型的
方式进行定义,也就是类级别的泛型。
类加载器
Java虚拟机中可以安装多个类加载器,系统默认主要是三个,每个负责加载特定的位置:
BootStrap,ExtClassLoader,AppClassLoader;
类加载本身也是一个java类。第一个类加载器不是java类。BootStrap
获取一个类额类加载器名字:
ClassLoaderTest.class.getClassLoader().getClass.getName;
委托加载机制
模板方法设计模式
5.代理
交叉业务,面向方面的编程AOP。解决交叉业务模块化
JVM在运行时动态生成类的字节码,这种动态生成的类往往被用作代理类。既动态代理类
JVM生成的动态代理类必须实现一个或多个接口,所以JVM生成的动态类只能用作具有相同接口的目标类的代理。
如果目标类没有实现接口。则可以CGLIB库可以动态生成一个类的子类。
Proxy.getProxyClass
实现类似Spring的可配置的AOP框架。
Spring两大核心:工厂,AOP框架
-----------------------------
泛型,代理和AOP需要继续巩固