동적 프록시의 특징:
객체를 프록시할 때 인터페이스를 구현할 필요가 없습니다.
프록시 객체 생성은 JDK API를 사용하여 프록시를 동적으로 구축하는 것입니다. (생성된 프록시 객체/대상 객체가 구현하는 인터페이스 유형을 지정해야 함)
동적 프록시의 다른 이름: JDK 프록시, 인터페이스 프록시
클래스 다이어그램:
Java 동적 프록시 클래스는 java.lang.reflect 패키지 아래에 있으며 일반적으로 다음 두 클래스를 포함합니다.
1 인터페이스 InvocationHandler: 이 인터페이스는 하나의 메소드만 정의합니다. 공용 객체 호출(객체 obj, 메소드 메소드) , Object [] args) 실제 사용에서 첫 번째 매개변수 obj는 일반적으로 프록시 클래스를 참조하고, method는 프록시 메소드, args는 메소드의 매개변수 배열을 나타냅니다. 이 추상 메서드는 프록시 클래스에서 동적으로 구현됩니다.
2. 프록시: 이 클래스는 동적 프록시 클래스입니다.
static Object newProxyInstance(ClassLoader loader, Class[] interfaces,InvocationHandler h):
프록시 클래스의 인스턴스를 반환합니다. 반환된 프록시 클래스는 프록시 클래스로 사용할 수 있습니다. (프록시 클래스의 인터페이스에 선언된 메서드를 사용할 수 있습니다.)
동적 생성의 구현 단계:
newProxyInstance(ClassLoader loader,Class[]
public interface Moveable { void move(); }
자동차가 있습니다:
//实现Moveable 接口,并随机暂停一段时间 import java.util.Random; public class Car implements Moveable{ @Override public void move() { try{ Thread.sleep(new Random().nextInt(1000)); System.out.println("汽车行驶中"); } catch (InterruptedException e) { e.printStackTrace(); } } }
Time 프록시 class:
import java.lang.reflect.InvocationHandler; import java.lang.reflect.Method; public class TimeHandler implements InvocationHandler{ public TimeHandler(Object target){ super(); this.target = target; } private Object target; /** * * @param proxy :被代理的对象 * @param method:被代理对象的方法 * @param args:方法的参数 * @return * @throws Throwable * 返回值:Object 方法的返回值 */ @Override public Object invoke(Object proxy, Method method, Object[] args) throws Throwable { long startTime = System.currentTimeMillis(); System.out.println("汽车开始行使"); method.invoke(target); long endTime = System.currentTimeMillis(); System.out.println("汽车行驶结束,行驶的时间为:"+(endTime-startTime)+"毫秒"); return null; } }
테스트 클래스:
import java.lang.reflect.InvocationHandler; import java.lang.reflect.Proxy; public class Test { public static void main(String[] args) { Car car = new Car(); InvocationHandler h = new TimeHandler(car); Class<?> cls = car.getClass(); /** * newProxyInstanced的参数 * 分别是:类加载器、实现的接口、实现的处理器 */ Moveable m = (Moveable) Proxy.newProxyInstance(cls.getClassLoader(), cls.getInterfaces(),h); m.move(); } }
출력 결과는 다음과 같습니다.
자동차가 운전을 시작합니다자동차가 운전 중입니다자동차가 운전을 종료하고 운전 시간은 137밀리초
참고:
//다음 시간은 무작위로 생성됩니다.
JDK 프록시는 인터페이스를 구현하는 클래스만 프록시할 수 있습니다. 인터페이스를 구현하지 않는 클래스는 프록시할 수 없습니다.
cglib의 원칙은 하위 클래스를 생성하는 것입니다. 지정된 대상 클래스에 대해 메소드를 재정의하여 향상을 달성하지만 상속을 사용하기 때문에 Xiaoying 자신이 이 영역을 완전히 파악하지 못하기 때문에 최종 수정된 클래스를 프록시할 수 없습니다. 여기에서 다른 블로그의 주요 기술 기사를 참조할 수 있습니다.
위 내용은 Java 프록시 패턴 예제 코드 분석의 상세 내용입니다. 자세한 내용은 PHP 중국어 웹사이트의 기타 관련 기사를 참조하세요!