Original link: http://www.orlion.ga/207/
First, Agent mode
Proxy mode is a frequently used design pattern, and the proxy mode is to provide proxy objects to the specified object. A reference to a specific object that is controlled by a proxy object.
Roles involved in proxy mode:
Abstract theme role: A public interface that declares a proxy theme and a real topic, so that any place that needs a real theme can be replaced with a proxy theme.
Agent-themed role: a reference with real-world themes that allows you to manipulate real-world themes at any time, and delegate themes to provide the same interface as the real theme, so that it can replace real-world themes at any time. The proxy topic, by holding a reference to a real topic, can not only control the creation or deletion of real topics, but can intercept real-world topics before they are called, or perform certain operations after they are called.
Real proxy object: Defines the specific object that the proxy role represents.
(Design pattern is universal)
The time-of-proxy classes created by the agent can be divided into two types:
Static proxy: The source code is generated automatically by the programmer or a specific tool, and then compiled. Before the program runs, the. class file for the proxy classes already exists.
Dynamic Agent: When the program is running, it is created dynamically using the reflection mechanism.
Second, static agent
Talk is cheap,show me the code
First define the interface of a winery:
Winefactory.java
Package ml.orlion.proxy; Public interface Winefactory {public void sell (); }
Then define a winery class to implement this interface:
Winefactoryimpl.java
Package ml.orlion.proxy; public class Winefactoryimpl implements winefactory{@Override public void Sell () {System.out.println ("liquor"); } }
Then define a proxy class to represent the winery:
Winefactoryproxy.java
Package ml.orlion.proxy; /** * Proxy class * WINEFACTORYIMPL Agent */public class Winefactoryproxy implements winefactory{private Wi Nefactory Winef; Public Winefactoryproxy (Winefactory winef) {this.winef = WINEF; } @Override public void Sell () {System.out.println ("before liquor ..."); Winef.sell (); System.out.println ("After the liquor ..."); } }
Third, dynamic agent
The code of the static agent can see that the static agent can only serve one interface, and if there are many interfaces in the project, there will be an excessive number of proxies. At this time, we need to use dynamic agent, a proxy class to complete all the agent functions. The bytecode of the dynamic proxy class is dynamically generated by the Java reflection mechanism when the program is run, without the programmer writing its source code manually. The dynamic proxy class not only simplifies programming, but also improves the scalability of the software system, because the Java reflection mechanism can generate any type of dynamic proxy class.
The JDK dynamic agent contains a Invocationhandler interface and a proxy class
(1) Invocationhandler interface
Public interface Invocationhandler {public object Invoke (Object Proxy,method method,object[] args) throws Thr owable; }
Where object porxy: is the agent
Method: Methods to invoke
object[] args: Parameter of the method to invoke
(2) proxy class
The proxy class is an action class that specifically completes the proxy, which can be used to dynamically generate an implementation class for one or more interfaces, which provides the following operations:
public static Object newproxyinstance (ClassLoader loader, class<?>[] interfaces, Invocationhandler h) throws Il Legalargumentexception
Wherein ClassLoader Loader: is the class loader;
(There are basically three kinds of loaders in Java:
Booststrap ClassLoader: This loader is written in C + + and is not visible in general development;
Extendsion ClassLoader: Used to load the extension class, generally corresponding to the class in the Jrelibext directory;
Appclassloader: (default) Loads the class specified by Classpath, which is most commonly used as an loader.
)
Class<?>[] Interfaces: get all interfaces;
Invocationhandler h: Gets the subclass instance of the Invocationhandler interface;
Code
Winefactory.java and Winefactoryimpl.java are the same code as static proxies.
Winefactoryinvocationhandler.java:
package ml.orlion.proxy; import java.lang.reflect.InvocationHandler; import java.lang.reflect.Method; &NBSP;&NBSP;&NBSP;&NBSP;&NBSP;&NBSP;&NBSP;/**&NBSP;&NBSP;&NBSP;&NBSP;&NBSP;*&NBSP;JDK Dynamic proxy class * Agent for Winefactoryimpl */ public class winefactoryinvocationhandler implements invocationhandler{ private Object target; @Override public object invoke (object porxy, method m, object[] args) throws Throwable { Object Result = null; beforemethod (); // Executive &NBSP;&NBSP;&NBSP;&NBsp;result = m.invoke (Target, args); aftermethod (); return result; } public void beforemethod () { system.out.println ("before the liquor ..."); } public void aftermethod () { system.out.println ("After the liquor ..."); } public object gettarget () { return target; } public void settarget (Object Target) { this.target = target; } }
Test:
Produces a proxied object winefactory wf = new Winefactoryimpl (); The Proxied object is given to Invocationhandler winefactoryinvocationhandler wfih = new Winefactoryinvocationhandler (); Wfih.settarget (WF); Generates an agent winefactory WFP = (winefactory) proxy.newproxyinstance (Wf.getclass () according to the Proxied object. getClassLoader (), Wf.getclass () . Getinterfaces (), WFIH); Wfp.sell ();
In addition to the JDK dynamic agent, there is also a cglib dynamic agent, the specific reference article (this reference): http://www.cnblogs.com/jqyp/archive/2010/08/20/1805041.html
Java Static agent and dynamic agent