关于JAVA的内省JavaBean、类加载器、类加载器的委托机制以及代理

知识点一:内省JavaBean(特殊的Java类)

1.类中的方法以set或get打头的类。可以将JavaBean当作普通的类来操作,而不可以将普通类当作JavaBean操作。

一个类当作JavaBean使用时,可以根据方法的名字推断出Java的属性名。去掉getset剩下的部分就是属性的名。

 剩下部分的第二个字母是小写,则第一个字母就是要变成小写。剩下部分的第二个字母是大写则第一个字母则是大写。

  如:getSun  属性名:sum

2.JavaBean包含的属性

boolean/Boolean :默认值为true      int/Integer;默认值为100

String:默认值为字符串                    double/Double:默认值为0.01D

例:      

Class e1=Class.forName("Three11.javaBeanElement");//获取测试类的字节码

Objectbean=e1.newInstance();//通过字节码获取对象

 BeanInfoinfo=Introspector.getBeanInfo(e1);//内省测试类,获取javaBean的属性信息

 PropertyDescriptor[]pds=info.getPropertyDescriptors();//获取javaBean属性数组

      //for迭代每个具体的属性

        for(PropertyDescriptor pd : pds)

        {

             //获取属性名

             Object name = pd.getName();

             //获取属性类型

             Object type =pd.getPropertyType();

             //获取get方法

             Method getMethod =pd.getReadMethod();

             //获取set方法

             Method setMethod =pd.getWriteMethod();

  

             //因为测试类是一个本类所以要去除它

             if(!"class".equals(name))

             {

                 //调用修改前的属性

                 if(getMethod!=null)

                  System.out.println("修改前:"+getMethod.invoke(bean,null));

                 //修改各种属性

                 if(type==String.class)

                       setMethod.invoke(bean,"www.itcast.com");

                 else if(type==boolean.class)

                       setMethod.invoke(bean,true);

                 else if (type==double.class)

                       setMethod.invoke(bean,0.01d);

                 else if(type==int.class)

                       setMethod.invoke(bean,100);

                 //调用修改后的属性

                 if(getMethod!=null)

                       System.out.println("修改后:"+getMethod.invoke(bean,null));

             }

        }

      

知识点二:类加载器与类加载器的委托机制

(1)类加载器:

类加载器就是加载类的工具,Jvm运行的时候需要加载class文件,在内存中字节码。

加载class,并生成字节码文件的过程是由类加载器完成的。因为类加载器也是java类,

任何类都是需要类加载器加载的,所以一定有一个不是java类的加载器,BootStrap,

Jvm还内置了2个类加载器,ExtClassLoader和AppClassLoader,他们是由BootStrap加载。

BootStrap:加载的是 java包,javax包,这些系统级的包,在JRE/lib/rt.jar包内。

ExtClassLoader则JRE/lib/ext/*.jar,这里是加载该目录下的所有jar包。

如果要手动编写System类的话就必须自己编写一个类加载器,不要委托机制才可以加载到。

(2)类加载器的委托机制

类加载器加载线程中的第一个类,如果这个类中还有其他类的话,则用这个类加载器加载其他的类。就是A类中引用了B类,

那么加载AB类的加载器都是同一个。每个类加载器加载类的时候都会委托给上级加载,当上级没有加载到这个类的话就返回

 给原加载器,如果还是加载不到就会报异常ClassnotFoundException。


例:

 class Test12{

        public static voidmain(String[]args)

        {

            for(String s:args)

           {System.out.println(s);

      }

    }

}


//测试的类

class javaBeanElement

{

 privateboolean flag;

 privateint x;

 private Stringstr;

 privatechar[] ch;

 privatelong l;

 privatedouble d;

 

 publicboolean isFlag() {

      returnflag;

 }

 publicvoid setFlag(boolean flag) {

      this.flag = flag;

 }

 publicint getX() {

      returnx;

 }

 publicvoid setX(int x) {

      this.x = x;

 }

 public String getStr() {

      returnstr;

 }

 publicvoid setStr(String str) {

      this.str = str;

 }

 publicdouble getD() {

      returnd;

 }

 publicvoid setD(double d) {

      this.d = d;

 }

 

 publicvoid show(long l)

 {

      this.l = l;

      System.out.println("http://www.itcast.com");

 }

}

 

 知识点三:代理

(1)面向方面的编程AOP(Aspect Oriented Program)

           系统中可能存在交叉业务需要切入到系统中的一方面,

如:

                安全       事务         日志
StudentService ---|----------|------------|-------------
CourseService ----|----------|------------|-------------
MiscService ------|----------|------------|-------------

面向方面的编程的目标就是要是交叉的业务模块化,可以采用将切面代码移动到原始方法的周围,这与直接在方法中编写切面代码运行起来的效果是一样的,如:

------------------------------------------------------切面
func1         func2           func3
{             {               { 
....            ....             ......
}             }               }
------------------------------------------------------切面
使用代理技术正好解决这样的问题,代理是实现AOP功能的核心和关键技术。

 

(2)Proxy类和InvocationHandler接口提供了生成动态代理的功能

例如:写一个ArrayList类的代理,实现和ArrayList中完全相同的功能,并可以计算每个方法运行的时间

publicclass Test1
{
   public staticvoid main(String[] args)
   { 
        //定义目标类
        ArrayListtarget = new ArrayList();
  
        //传递目标和系统功能到获取代理的函数//这里创建代理的时候必须是目标的父类
        ListproxyList = (List)getProxy(target,new getSystemRunTime());
  
        //使用返回的代理并计算使用了多少时间
        proxyList.add(1);
        proxyList.remove(0);
        proxyList.size();
  
   }
 
   public staticObject getProxy(finalObject target,final getSystemRunTime time)
   { 
          //建立代理
          Object proxy = Proxy.newProxyInstance(
              target.getClass().getClassLoader(),//定义代理类的类加载器
              target.getClass().getInterfaces(),//代理类要实现的接口列表
              new InvocationHandler()   //调用处理程序
              {
                   public Object invoke(Object proxy,Method method,Object[] args)throwsThrowable
                   { 
                        //目标执行前代码
                        time.beforeCode();
      
                        //为了方便观看,设置了sleep
                        Thread.sleep(newRandom().nextInt(200));
                        //调用目标方法
                        Object obj = method.invoke(target, args);
      
                        //目标执行后代码
                        time.afterCode(method);
                        return obj;
                   }
              });
        //返回代理
        return proxy;
   }
}

 

//抽取出来的功能系统模版
abstract interface proxyAdvise
{
   abstract void beforeCode();
   abstract void afterCode(Method method);
}

//功能系统计算程序运行的时间
class getSystemRunTime implementsproxyAdvise
{

   privatelong starttime;

   publicvoid beforeCode()
   { 
        //获取目标程序运行前的时间
        starttime = System.currentTimeMillis();
   }

   publicvoid afterCode(Method method)
   { 
        //获取目标程序运行后的时间并显示总共运行了多久
        longendtime = System.currentTimeMillis();
        System.out.println(method.getName()+"\t"+"method is ran "+"\t"+(endtime-starttime)+" ms");
   }
} 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值