代理模式有静态代理模式和动态代理模式
1.静态代理模式:
这个例子举得太好了:助理可以做其他事情:预定时间,场地,最后结算费用,但是唱歌的话只能由歌手华仔本人来
总共有三个类,调用类,代理类,被代理类
从这辐图里面你要得到两个信息
(1)代理类和被代理的类实现同一个接口request()
(2) 代理类除了实现接口里面的方法之外,还额外有自己的其他方法,比如这里的afterRequest方法和preRequest方法,显然这样扩展了被代理类的功能
一个很详细详细的例子:
总结就是:不再直接调用类C的function1方法
而是先调类B的function1方法,然后在类B的function1方法中调用类C的func1方法,直接调用变成间接调用
public interface D
{
public void function1();
}
class C implement D
{
@Override
public void function1()
{
System.out.println("111111");
}
}
class B implement D
{
private C c;
//构造方法
public B(C c)
{
this.c=c;
}
@Override
public void function1()
{
c.function1();
}
@Override
public void function2()
{
System.out.println("2222222");
}
}
public class A
{
public static void main(String[] args)
{
C c=new C();
B b=new B(c);
b.function1();
}
}
2.动态代理(也叫jdk代理)
总结:业务接口中增加方法,增加功能
但是代理类这个类里面一行代码都不用改
也就是说代理类可以根据你要调用的方法,来进行变化,最后让你成功的调用方法
agent.show()可以,agent.dance()也可以,agent.show()也可以
public interface SuperStar
{
public void sing();
}
public class SuperStarLiu implements SuperStar
{
@Override
public void sing()
{
System.out.println("我是刘德华,我正在表演唱歌.......");
}
}
public class SuperStarZhou implements SuperStar
{
@Override
public void sing()
{
System.out.println("我是周润发,我正在表演唱歌.......");
}
}
//动态代理类Proxy
public class Proxy
{
SuperStar target;
public Proxy()//构造方法
{
this.target=target;
}
//返回一个动态代理对象,由于这个对象可以是任意类型,所以返回值是Object类型
public Object getAgent()
{
return Proxy.newProxyInstance(loader,intrtfances,h:);
//固定写法,记住就行
//loader换成target.getClass().getClassLoader()
//interfaces换成target.getClass().getInterfaces()
//h:换成
//new InvocationHandler()
{
@Override
public Object invoke(Object proxy,Method method,Object[] args)
{
System.out.println("预定时间......");
System.out.println("预定场地......");
method.invoke(target,args);
//这行代码封神了,这句代码既可以调用target.sing(),又可以调用target.show(),还可以调用target.dance(),非常灵活,可以调用任何方法
System.out.println("结算费用......");
return obj;
}
}
}
}
//第一个测试代码:
Proxy proxy=new Proxy(new SuperStarZhou());
SuperStar agent=(SuperStar) proxy.getAgent();
agent.sing();
//得到输出结果如下:
//预定时间......
//预定场地......
//我是周润发,我正在表演唱歌.......
//结算费用........
//第二个测试代码:
此时,如果在业务接口中增加一个方法(增加一个功能):
public String show(int age);
public interface SuperStar
{
public void sing();
public String show(int age);
}
SuperStarLiu类和 SuperStarZhou类都要重写这个方法
比说:
public class SuperStarLiu implements SuperStar
{
@Override
public void sing()
{
System.out.println("我是刘德华,我正在表演唱歌.......");
}
@Override
public String show(int age)
{
System.out.println("刘德华的show......."+age);
return "liu";
}
}
但是,代理类中一行代码都不用改
Proxy proxy=new Proxy(new SuperStarLiu());
SuperStar agent=(SuperStar) proxy.getAgent();
agent.show(60);
//得到输出结果如下:
//预定时间......
//预定场地......
//周润发的show.......66
//结算费用........
//如果想看agent.show(60)的返回值,可以:
String s=agent.show(60);
System.out.println(s);
//liu