代理模式的定义为:为其他对象提供一个代理来控制对它的访问。
英文定义:Provide a surrogate or placeholder for another object to control access to it.
这个中文定义没有很好的反映出原本的意思。英文定义中的surrogate与placeholder都有代理的意思。但是他们之间肯定存在微妙的差别。
以下翻译结果,来自有道
public interface PersonBean { String getName(); String getGender(); String getInterests(); int getHotOrNotRating(); void setName(String name); void setGender(String gender); void setInterests(String interests); void setHotOrNotRating(int rating); }
public class PersonBeanImpl implements PersonBean { String name; String gender; String interests; int rating; int ratingCount = 0; public String getName() { return name; } public String getGender() { return gender; } public String getInterests() { return interests; } public int getHotOrNotRating() { if (ratingCount == 0) return 0; return (rating / ratingCount); } public void setName(String name) { this.name = name; } public void setGender(String gender) { this.gender = gender; } public void setInterests(String interests) { this.interests = interests; } public void setHotOrNotRating(int rating) { this.rating += rating; ratingCount++; } }
import java.lang.reflect.*; public class OwnerInvocationHandler implements InvocationHandler { PersonBean person; public OwnerInvocationHandler(PersonBean person) { this.person = person; } public Object invoke(Object proxy, Method method, Object[] args) throws IllegalAccessException { try { if (method.getName().startsWith("get")) { return method.invoke(person, args); } else if (method.getName().equals("setHotOrNotRating")) { throw new IllegalAccessException(); } else if (method.getName().startsWith("set")) { return method.invoke(person, args); } } catch (InvocationTargetException e) { e.printStackTrace(); } return null; } }
import java.lang.reflect.*; public class NonOwnerInvocationHandler implements InvocationHandler { PersonBean person; public NonOwnerInvocationHandler(PersonBean person) { this.person = person; } @Override public Object invoke(Object proxy, Method method, Object[] args) throws Throwable { try { if (method.getName().startsWith("get")) { return method.invoke(person, args); } else if (method.getName().equals("setHotOrNotRating")) { return method.invoke(person, args); } else if (method.getName().startsWith("set")) { throw new IllegalAccessException(); } } catch (InvocationTargetException e) { e.printStackTrace(); } return null; } }
import java.lang.reflect.*; import java.util.ArrayList; public class MatchMakingTestDrive { // instance variables here ArrayList<PersonBean> persons; public static void main(String[] args) { MatchMakingTestDrive test = new MatchMakingTestDrive(); test.drive(); } public MatchMakingTestDrive() { initializeDatabase(); } public void drive() { PersonBean joe = getPersonFromDatabase("Joe Javabean"); PersonBean ownerProxy = getOwnerProxy(joe); System.out.println("Name is " + ownerProxy.getName()); ownerProxy.setInterests("bowling, Go"); System.out.println("Interests set from owner proxy"); try { ownerProxy.setHotOrNotRating(10); } catch (Exception e) { System.out.println("Can't set rating from owner proxy"); } System.out.println("Rating is " + ownerProxy.getHotOrNotRating()); PersonBean nonOwnerProxy = getNonOwnerProxy(joe); System.out.println("Name is " + nonOwnerProxy.getName()); try { nonOwnerProxy.setInterests("bowling, Go"); } catch (Exception e) { System.out.println("Can't set interests from non owner proxy"); } nonOwnerProxy.setHotOrNotRating(3); System.out.println("Rating set from non owner proxy"); System.out.println("Rating is " + nonOwnerProxy.getHotOrNotRating()); } PersonBean getOwnerProxy(PersonBean person) { return (PersonBean)Proxy.newProxyInstance( person.getClass().getClassLoader(), person.getClass().getInterfaces(), new OwnerInvocationHandler(person)); } PersonBean getNonOwnerProxy(PersonBean person) { return (PersonBean)Proxy.newProxyInstance( person.getClass().getClassLoader(), person.getClass().getInterfaces(), new NonOwnerInvocationHandler(person)); } private void initializeDatabase() { persons = new ArrayList<PersonBean>(); PersonBean personBean = new PersonBeanImpl(); personBean.setName("Joe Javabean"); personBean.setGender("male"); personBean.setInterests("Drinking"); personBean.setHotOrNotRating(2); persons.add(personBean); } private PersonBean getPersonFromDatabase(String name) { for (PersonBean person : persons) { if (person.getName().equals(name)) { return person; } } return null; } }