Java学习:动态代理
创始人
2024-02-17 16:12:58
0

java

    • 一、代理模式
    • 二、静态代理
    • 三、动态代理

一、代理模式

  • 代理模式是一种设计模式,能够使得再不修改源目标的情况下,额外扩展源目标的功能。即通过访问源目标的代理类,再由代理类去访问源目标。这样一来,要扩展功能,就无需修改源目标的代码了。只要在代理上增加就可以了

二、静态代理

  • 就是通过声明一个明确的代理类来访问源对象
    假设有一个Person接口和一个Aniaml接口
package StaticProxy;
//里面有wakeup和sleep两个方法
public interface Person {void wakeup();void sleep();
}
package StaticProxy;public interface Animal {void wakeup();void sleep();
}

它们有各自的实现类,以student和dog举例

package StaticProxy;public class Student implements Person{private String name;public Student(String name){this.name = name;}@Overridepublic void wakeup() {System.out.println("学生" + name + "起床了");}@Overridepublic void sleep() {System.out.println("学生" + name + "睡觉了");}
}
package StaticProxy;public class Dog implements Animal{private String name;public Dog(String name){this.name = name;}@Overridepublic void wakeup() {System.out.println("dog" + name + "起床了");}@Overridepublic void sleep() {System.out.println("dog" + name + "睡觉了");}
}

这时候假设我们现在要在wakeup()前增加一行输出"早安",sleep()前增加一行输出"晚安",通过直接修改实现类肯定是不大好的,这里列举了student和dog,肯定会有很多种类,一个个修改工作量太大了,可以针对两个接口实现两个动态代理类

package StaticProxy;public class PersonProxy implements Person{private Person person;public PersonProxy(Person person){this.person = person;}@Overridepublic void wakeup() {System.out.println("早安");person.wakeup();}@Overridepublic void sleep() {System.out.println("晚安");person.sleep();}
}
package StaticProxy;public class AnimalProxy implements Animal{private Animal animal;public AnimalProxy(Person person){this.animal = animal;}@Overridepublic void wakeup() {System.out.println("早安");animal.wakeup();}@Overridepublic void sleep() {System.out.println("晚安");animal.sleep();}
}

如上所示,在代理类中增加打印"早安"和"晚安",最终执行代码如下

package StaticProxy;public class MainApp {public static void main(String[] args) {Person student = new Student("李世民");PersonProxy personProxy = new PersonProxy(student);personProxy.wakeup();personProxy.sleep();Person student1 = new Student("朱元璋");PersonProxy personProxy1 = new PersonProxy(student1);personProxy.wakeup();personProxy.sleep();Animal animal = new Dog("王专家");AnimalProxy animalProxy = new AnimalProxy(animal);animalProxy.wakeup();animalProxy.sleep();Animal animal1 = new Dog("李专家");AnimalProxy animalProxy1 = new AnimalProxy(animal1);animalProxy.wakeup();animalProxy.sleep();}
}

在这里插入图片描述
这种模式很好理解,这里用了两个代理类,分别代理了Person和Animal接口,但是缺点也很明显:

  • 会存在大量的冗余的代理类,这里演示了两个接口,如果有10个接口,就必须定义10个代理类
  • 不易维护,一旦接口更改,代理类和目标类都需要更改

三、动态代理

  • 无需声明式的创建java代理类,而是在运行过程中生成"虚拟"的代理类,被classloader加载。从而避免了静态代理那样需要声明大量的代理类
  • 动态代理也称为接口代理,说白了只是根据接口"凭空"来生成类,至于具体的执行,都被代理到了InvocationHandler的实现类里

用JDK动态代理实现上述例子

package RunProxy;import java.lang.reflect.InvocationHandler;
import java.lang.reflect.Method;public class JdkProxy implements InvocationHandler {private Object bean;public JdkProxy(Object bean){this.bean = bean;}@Overridepublic Object invoke(Object proxy, Method method, Object[] args) throws Throwable {String methodName = method.getName();if (methodName.equals("wakeup")){System.out.println("早安");}else if (methodName.equals("sleep")){System.out.println("晚安");}return method.invoke(bean,args);}
}

执行代码

package RunProxy;import StaticProxy.Animal;
import StaticProxy.Dog;
import StaticProxy.Person;
import StaticProxy.Student;
import java.lang.reflect.Proxy;public class MainApp {public static void main(String[] args) {JdkProxy proxy = new JdkProxy(new Student("李世民"));Person student = (Person) Proxy.newProxyInstance(proxy.getClass().getClassLoader(),new Class[]{Person.class},proxy);student.wakeup();student.sleep();proxy = new JdkProxy(new Student("朱元璋"));Person student1 = (Person) Proxy.newProxyInstance(proxy.getClass().getClassLoader(),new Class[]{Person.class},proxy);student1.wakeup();student1.sleep();proxy = new JdkProxy(new Dog("王专家"));Animal animal = (Animal) Proxy.newProxyInstance(proxy.getClass().getClassLoader(),new Class[]{Animal.class},proxy);animal.wakeup();animal.sleep();proxy = new JdkProxy(new Dog("李专家"));Animal animal1 = (Animal) Proxy.newProxyInstance(proxy.getClass().getClassLoader(),new Class[]{Animal.class},proxy);animal1.wakeup();animal1.sleep();}
}

相关内容

热门资讯

思想政治工作条例最新修订内容,... 思想政治工作条例最新修订内容,思想政治工作条例全文下载 思想政治工作条例最新修订,全文下载与深度解读...
CBA潜力赛为何打成“老将赛”... 计时钟归零,双方教练握手致意,观众开始退场,CBA联赛的正赛宣告结束。然而球场并未就此沉寂,替补席上...
“手术钻头断裂遗留患者体内”,... 12月21日,湖南祁阳市卫生健康局发布情况通报称,近日,有媒体报道祁阳市中医医院发生骨科手术钻头断裂...
代驾纠纷 代驾时撞伤行人、车辆发生故障…… 这些都和车主无关,应由代驾赔偿? 观点: 使用代驾服务并非将所有...
公司股东与妻子分居期间出轨女下... 近日据报道,宁夏永宁县人民法院一审查明公司股东李某乙在与妻子李某甲分居期间,与公司女员工马某某存在不...
动物学家、律师和创作者,Thi... 12月21日,以“一起·了不起”为主题的2025 ThinkPad黑FUN礼在京举办。活动现场,律师...
徐奇渊:扩内需与对外政策紧密相... 近日,中国海关总署发布了一组数据令人关注:2025年前11个月,我国货物贸易顺差达到1.08万亿美元...
46岁上海独居女子不幸离世,官... 居住在上海虹口区46岁的蒋女士因突发脑溢血于今年10月入院,远亲吴先生与其公司共同垫付了医药费,但她...
威海市汽车以旧换新补贴政策调整... 根据稳妥有序开展消费品以旧换新工作统一部署,经研究决定,对我市汽车以旧换新补贴政策进行调整。现将有关...