类加载器(ClassLoader):
负责将.class文件加载到内存中,并为之生成对应的Class对象,也就是字节码文件对象。
问题:我们平时书写在idea中的Java程序是如何运行的呢?
1) 首先将 .java 源文件编译为class类文件,存在硬盘中
2) jvm通过类加载器ClassLoader把硬盘中的class文件加载到内存中,
便能使用该类中的成员变量和方法了。
加载到内存中这个class文件就会变成一个Class类的对象。
常见的类加载器有三种,每个类加载器负责加载不同位置的类:
1. Bootstrap 根类加载器; JRE/lib/rt.jar
2. ExtClassLoader 扩展类加载器; JRE/lib/ext/ *.jar
3. AppClassLoader 系统/应用类加载器; ClassPath指定的所有jar或目录
说明:
1 Bootstrap 是最顶级的类加载器。它加载类文件不是我们自己书写的。都是sun公司定义好的类,比如String、Integer、File类等。
2 ExtClassLoader 扩展类加载器,加载的都是jdk内部自己使用的类。
3 AppClassLoader 系统/应用类加载器,是用来加载ClassPath 指定的所有jar或目录,ClassPath表示存放类路径的,我们如果不配置ClassPath,那么就表示当前文件夹,在idea环境下的ClassPath是out中的目录。在out目录存放的都是我们书写好的class文件,也就是说 AppClassLoader 类加载器是用来加载我们书写的out目录下的class文件。
代理模式:
演示:
1 代理:代理对象主要用来拦截目标业务对象(被代理对象)的访问。
举例:代理对象为明星的经纪人,目标业务对象为明星,
如果其他公司想和这个明星合作,那么就会找他的代理对象即经纪人。
然后经纪人(代理对象)把访问明星的公司(目标业务对象)给拦截,具体什么需求直接找代理对象即经纪人
2 代理对象要持有真实业务对象。在代理类中创建被代理类的对象。
3 代理对象要和真实业务对象,具备相同的行为方法。实现同一个接口。
4 代理对象拦截对真实对象的访问,可以修改访问的参数、返回值,甚至拦截访问。
代理模式代码演示如下所示:
1 定义一个测试类ProxyDemo1,并定义一个main函数;
2 定义一个接口Star,有着几个函数sing(double money)、liveShow(double money)、sleep();
3 在定义一个目标业务对象即某个明星类,LiuYan 并实现 Star 接口,那么要在明星类复写Star接口中的函数,并在函数体书写实现的代码;
4 在定义一个代理对象即明星经纪人的类,SuoGe 并实现 Star 接口,那么要在经纪人类复写Star接口中的函数,并在函数体书写实现拦截明星类对象访问的代码
代理和被代理对象实现的接口:
public interface Star {
public abstract void sing(double money);
public abstract void liveShow(double money);
public abstract void sleep();
}
被代理类即明星的代码:
public class LiuYan implements Star{
public void sing(double money) {
System.out.println("唱了一首:甜蜜蜜");
System.out.println("赚了"+money+"元");
}
public void liveShow(double money) {
System.out.println("参加了:奔跑吧,兄弟");
System.out.println("赚了"+money+"元");
}
public void sleep() {
System.out.println("好累啊,休息一会。。。。。");
}
}
代理对象即经纪人的代码如下所示:
public class SuoGe implements Star {
private LiuYan ly = new LiuYan();
public void sing(double money) {
if (money < 100000) {
System.out.println("滚,穷屌丝,一边玩泥巴去");
return;
}
System.out.println("我抽取了" + money * 0.2 + "元代理费用");
ly.sing(money * 0.8);
}
public void liveShow(double money) {
if (money < 500000) {
System.out.println("滚,穷屌丝,一边玩泥巴去");
return;
}
System.out.println("我抽取了" + money * 0.2 + "元代理费用");
ly.liveShow(money * 0.8);
}
public void sleep() {
ly.sleep();
}
}
测试类中的主函数代码:
public class ProxyDemo {
public static void main(String[] args) {
SuoGe sg = new SuoGe();
sg.sing(200000);
System.out.println("-----------------------------------");
sg.liveShow(1000000);
System.out.println("-----------------------------------");
sg.sleep();
}
}