Java什么是代理,代理java作用
如何解决写爬虫IP受阻的问题?立即使用。
java什么是代理?
代理是一种设计模式,提供了另一种访问目标对象的方式,即通过代理对象访问目标对象。您可以扩展目标对象的功能,而无需对其进行修改。
代理的作用:减少代码的冗余。
代理模式的实现可以分为静态实现和动态实现两大类,动态实现又可以分为jdk动态实现和cglib动态实现。
Java的三种代理模式
实现上述要求有三种方式。这部分只看三种模式的代码怎么写,先不谈实现原理。
1.静态代理
公共接口是整数{
void sing();
}
/**
*目标对象实现一个接口
*/
公开课歌手实现ISinger{
public void sing(){
System.out.println(唱首歌);
}
}
/**
*代理对象和目标对象实现相同的接口。
*/
公共类SingerProxy实现ISinger{
//接收目标对象以调用sing方法
私有ISinger目标;
公共UserDaoProxy(ISinger目标){
this.target=target
}
//扩展目标对象sing方法的功能
public void sing() {
System.out.println(向观众问好);
target . sing();
System.out.println(谢谢大家);
}
}测试
/**
*测试类别
*/
公共类测试{
公共静态void main(String[] args) {
//目标对象
is inger target=new Singer();
//代理对象
is inger proxy=new singer proxy(target);
//执行代理的方法。
proxy . sing();
}
优点:在不修改目标对象功能的情况下,扩展目标功能。
缺点:这种实现直观简单,但缺点是代理对象必须提前编写,如果接口层发生变化,必须维护代理对象的代码。如果可以在运行时动态编写代理对象,不仅可以减少大量的代理代码,减少不断维护的麻烦,但是运行效率肯定会受到影响。这种方式就是下一个动态代理。
2.JDK代理商
和静态代理的前提一样,还是要扩展Singer对象。
公共接口是整数{
void sing();
}
/**
*目标对象实现一个接口
*/
公开课歌手实现ISinger{
public void sing(){
System.out.println(唱首歌);
}
}这次是直接测试。因为java底层封装了实现细节(后面会详细讨论),所以代码非常简单,格式基本固定。
只需调用代理类的静态方法newProxyinstance,就会返回代理类对象。
静态对象new proxy instance(Class loader loader,Class?[]接口,调用处理程序h)按顺序接收三个参数:
ClassLoader:指定当前目标对象使用类加载器,写入方式固定。
阶级?[]接口:目标对象实现的接口类型,以固定的方式编写。
InvocationHandler h:事件处理接口,需要一个实现类。一般直接使用匿名内部类。
试验码
公共类测试{
公共静态void main(String[] args) {
歌手目标=新歌手();
is inger proxy=(is inger)proxy . new proxy instance(
target.getClass()。getClassLoader(),
target.getClass()。getInterfaces(),
新的InvocationHandler() {
@覆盖
公共对象调用(对象代理、方法方法、对象[]参数)抛出Throwable {
System.out.println(向观众问好);
//执行目标对象方法
object return value=method . invoke(target,args);
System.out.println(谢谢大家);
返回returnValue
}
});
proxy . sing();
}
}优点:动态实现扩展,不改变目标对象的逻辑。
缺点:可以看出,静态代理和JDK代理有一个共同的缺点,就是目标对象必须实现一个或多个接口,否则无法实现动态代理。
3.Cglib代理
先决条件:
有必要介绍一下cglib的jar文件。由于Spring的核心包已经包含了Cglib函数,所以也可以直接引入Spring-Core-3.2.5.jar。
目标类不能是最终的。
如果目标对象的方法是final/static,则不会被拦截,即不会执行目标对象的附加业务方法。
/**
*目标对象,它不实现任何接口。
*/
公开课歌手{
public void sing() {
System.out.println(唱首歌);
}
}/**
* Cglib子类代理工厂
*/
公共类ProxyFactory实现MethodInterceptor{
//维护目标对象
私有对象目标;
公共代理工厂(对象目标){
this.target=target
}
//为目标对象创建代理对象
公共对象getProxyInstance(){
//1.工具类别
Enhancer en=新增强子();
//2.设置父类
en . set super class(target . getclass());
//3.设置回调函数
en . set callback(this);
//4.创建子类(代理对象)
返回en . create();
}
@覆盖
公共对象拦截(对象对象,方法方法,对象[]参数,方法代理代理)抛出Throwable {
System.out.println(向观众问好);
//执行目标对象的方法
object return value=method . invoke(target,args);
System.out.println(谢谢大家);
返回returnValue
}
}这里的代码也很固定,只有黄色部分需要自己写。
试验
/**
*测试类别
*/
公共类测试{
公共静态void main(String[] args){
//目标对象
歌手目标=新歌手();
//代理对象
Singer proxy=(Singer)new proxy factory(target)。getProxyInstance();
//执行代理对象的方法
proxy . sing();
}
}优点:动态实现扩展,不改变目标对象的逻辑。
缺点:目标必须实现接口,否则无法实现动态代理。
总结:三种代理模式各有优缺点和相应的适用范围,主要看目标对象是否实现接口。以Spring框架选择的代理模式为例。
那是java。什么是代理?更多详情请关注我们的其他相关文章!
郑重声明:本文由网友发布,不代表盛行IT的观点,版权归原作者所有,仅为传播更多信息之目的,如有侵权请联系,我们将第一时间修改或删除,多谢。