`
zhongsw
  • 浏览: 24385 次
文章分类
社区版块
存档分类
最新评论

黑马程序员_Java高新技术知识要点

阅读更多

---------------------- android培训java培训 、期待与您交流! ----------------------

 

 

 

 

 

内省 :IntroSpector 主要对 JavaBean 进行操作 .

JavaBean 是符合某种特殊的规则 Java .

比如 :getAge()   setAge()

class Person{

       private int x;

       public int get Age(){

              return x;

       }

       public void setAge(){

              this.x=age;

       }

}

JavaBean 来说 ,Person 有的属性是 Age 属性 .  按普通类来操作属性是 x.

去掉 set get 后面的就是 JavaBean 属性名 .

书写规则 : 如果第二个字母是小的 , 则把第一个字母也变成小的 .

PropertyDescriptor

PropertyDescriptor 描述 Java Bean 通过一对存储器方法导出的一个属性。

ReflectPoint pt1=new ReflectPoint(3,5);

String propertyName=”x”;

PropertyDescriptor pd=new PropertyDescriptor(propertyName,pt1.getClass());

Method methodGetx=pd.getReadMethod();

Object retval=methodGetx.invoke(pt1);

 

JavaBean BeanUtils 工具包 , String 类型操作参数的数据 .

导入 jar . 为了让工程发给其他人后其他人也能够用 . 要把 jar 包放在工程下面 ,Build Path à add to Build Path

有时候导入的 jar 包又引用了第三方的 jar , 一样要导入这个第三方的 jar .

JDK1.7 新特性 Map 集合可以写成

  Map map={name:”zxx”,age:32};

PropertyUtils 按实际类型操作参数的数据 .

 

 

JDK1.5 另外一个新特性 : 注解 Annotation

注解以 @ 打头 .

@Suppresswarnings(“deprecation”)  不要警告过时信息 .

@Deprecated  声明过时

@Override     对父类的方法复写

注解相当于一种标记 , 在程序中加上注解就等于为程序打上了某种标记 , 以后 ,javac 编译器 , 开发工具和其他程序可以用反射来了解你的类及各种元素上有无何种标记 , 就去做些相应的事 .

标记可以加在包 , , 字段 , 方法 , 方法的参数以及局部变量上 .

如何应用注解 :

注解就相当于一个你的源程序中要调用的一个类 , 要在源程序中应用某个注解 , 得先准备好这个注解类 . 就像你要调用某个类 , 得先开发好这个类 .

注解类 , 在类前加

@retention(RetentionPolicy.RUNTIME)// 为注解加的注解 . 称为无注解 .

pulic @interface a{}

应用了注解类的类

@A

Class B{}

对应用了注解类的类进行反射操作的类

Class C{

       B.class.isAnnotionPresent(A.class);

       A a=B.class.getAnnotion(A.class);

}

 

一个注解的生命周期有三个阶段 :

Java 源文件            class 文件               内存中的字节码

 

为注解增加属性 .@MyAnnotation(color=”red”)

如果数组属性中只有一个元素 , 这时候属性值部分可以省略大括号 .

 

 

JDK1.5 的又一新特性泛型 .

泛型可以限定类型 , 让在运行时出现的一些问题提到编译时期 . 省去一些麻烦 , 一些对象不用强制类型转换了 .

泛型是给编译器看的 , 在编译后泛型信息就不存在了 .

因此可以用反射的方法来操作泛型来添加不同元素类型 .

在下面整型的 collection 集合中可以添加 string 类型的字符串

ArrayList<Integer> collection = new ArrayList<Integer>();

collection.getClass().getMethod("add", Object.class ).invoke(collection, "itcast");

 

泛型术语 :ArrayList<E> 类定义和 ArrayList<Integer> 类引用中涉及如下术语 .

整个称为 ArrayList<E> 泛型类型

E 称为类型变量或类型参数

整个 ArrayList<Integer> 称为参数化的类型 .

Integer 称为类型参数的实例或实际类型参数 .

< > typeof

ArrayList 称为原始类型 .

 

参数化类型与原始类型的兼容性 :

1.       参数化类型可以引用一个原始类型的对象 .

2.       原始类型可以引用一个参数化的对象 .

 

参数化类型不考虑类型参数的继承关系 .

在创建数组实例时 , 数组的元素不能使用参数化的类型 .

Vector<Integer> VectorList[]=new Vector<integer>[10];// 会报错

 

泛型通配符的扩展 :

? 表示可以指向任意类型 . 用了后不能调用与参数类型有关的方法 .

使用 ? 通配符可以引用其他各种参数化的类型 ,? 通配符定义的变量主要用作引用 , 可以调用与参数化无关的方法 , 不能调用与参数化有关的方法 .

通配符的扩展

向上限定 :<?extends Number> 表示只能是 Number Number 的子类 .

向下限定 <?super Integer>    表示只能是 Integer Integerr 的父类 .

只有引用类型才能作为泛型方法的实际参数 . 基本类型不可以 , 有时候会自动装拆箱 . 泛型可以用 & 来指定多个边界 .

 

如果类的实例对象中的多处都要用到同一个泛型参数 , 即这些地方引用的泛型类型要保持同一个实际类型时 , 这时候就要采用泛型类型的方式进行定义 , 也就是类级别的泛型 , 语法格式如下 :

public class GenericDao<T>{

       private T fild1;

       public void save(T obj){}

       public T getByld(int id){}

}

 

 

类加载器 : 加载类的工具 .

我们在程序中用到一个类 , 首先会把这个类的字节码加载到程序中来 . 这就要类加载器来做 .

Java 虚拟机有多个类加载器 . 有三个主要的 .

BootStrap,ExtClassLoader,AppClassLoader

类加载器也是一个类 , 需要被加载 . 第一个类加载器是 BootStrap, 他是随虚拟机启动 . 不需要别人加载 .

ClassLoaderTest.class.getClassLoader().getClass().getName();

 

BootStrap 加载 JRE/lib/rt.jar

ExtClassLoader 加载 JRE/lib/ext/*.jar

AppClassLoader 加载 CLASSPATH 指定的所有 jar 或目录 .

类加载器的委托机制 . 如果父类里边有该类就父类加载 , 没有在向子类查找 .

 

编写自己的类加载器 .   有包名的类不能调用无包名的类 .

引出模板方法设计模式 .

自定义的类必须继承 ClassLoader, 而且要复写父类的 findClass 方法 .

 

class NetworkClassLoader extends ClassLoader {
       String host;
       int port;
       public Class findClass(String name) {
           byte[] b = loadClassData(name);
           return defineClass(name, b, 0, b.length);
       }

       private byte[] loadClassData(String name) {
           // load the class data from the connection
            . . .
       }
 }

 

 

 

 

代理的概念与作用 :      Proxy

要为已存在的多个具有相同接口的目标的各个方法增加一些系统功能 , 例如 , 异常处理 , 日志 , 计算方法的运行时间 , 事务管理 , 等等 .

代理类的每个方法调用目标类的相同方法 , 并在调用方法时加上系统功能的代码 .

采用工厂模式和配置文件的方式进行管理 .

面向方面的编译 .AOP(Aspect Oriented Program)

 

Proxy.getProxyClass(ClassLoader,interfaces)

上面的类加载器通常使用和后面接口相同的类加载器 .

Proxy.getProxyClass(collection.class.getClassLoader(), collection.class)

通过上面返回的 Class 文件可以用反射来查到该代理类的构造函数和方法 . 查看后发现该代理类只有一个有参的构造方法 , 参数为 InvocationHandler 对象 .

创建此代理类的实例对象只能用这个有参的构造方法来 newInstance. 这时要用到参数对象 , InvocationHandler 查看后发现是一个接口 , 所以要自己创建一个它的子类对象给构造函数调用 . 发现获得的实例对象的 toString 方法返回的是 null.  只能调用该对象的无返回值类型的方法 .

InvocationHandler 可以用匿名内部类来实现 , 在这个匿名内部类中也可以定义对象 , 方法 .

 

Collection proxy=(Collection)Proxy.newProxyInstance(
    target.getClass().getClassLoader(),
    target.getClass().getInterfaces(),
    //匿名内部类来实例化InvocationHandler对象.
    new InvocationHandler() {

     @Override//复写父类的invoke方法.
     public Object invoke(Object proxy, Method method, Object[] args)
       throws Throwable {
      long beginTime=System.currentTimeMillis();
      Object retVal=method.invoke(target, args);//调用目标的运行方法.
      long endTime=System.currentTimeMillis();
      System.out.println(method.getName()+"方法运行时间为"+(endTime-beginTime));
      return retVal;
     }
    }
    );

 

 

 

---------------------- android培训java培训 、期待与您交流! ----------------------

分享到:
评论

相关推荐

Global site tag (gtag.js) - Google Analytics