Das Verstehen und Verwenden von Designmustern kann unsere guten objektorientierten Programmiergewohnheiten kultivieren. Gleichzeitig können wir uns in praktischen Anwendungen so wohl fühlen wie ein Fisch im Wasser und den Spaß an der Leichtigkeit genießen.
Proxy ist ein nützlicherer Modus, und es gibt viele Varianten. Die Anwendungsszenarien decken kleine Strukturen bis hin zu großen Strukturen ab. Proxy bedeutet Proxy Kann Die Erklärung lautet: Zwischen dem Startpunkt und dem Ziel gibt es eine Zwischenschicht, was Agentur bedeutet.
Entwurfsmuster definiert: Stellen Sie einen Proxy für andere Objekte bereit, um den Zugriff auf dieses Objekt zu steuern.
Warum den Proxy-Modus verwenden?
1. Autorisierungsmechanismus Benutzer auf verschiedenen Ebenen haben unterschiedliche Zugriffsrechte auf dasselbe Objekt. Im Jive-Forumsystem wird beispielsweise Proxy verwendet, um den Autorisierungsmechanismus zu steuern und auf das Forum zugreifen. Es gibt zwei Arten von Personen: registrierte Benutzer und Besucher (nicht registrierte Benutzer). Jive verwendet Agenten wie ForumProxy, um die Zugriffsrechte dieser beiden Benutzer auf das Forum zu steuern.
2. Ein Client kann ein Objekt nicht direkt bedienen, sondern muss mit diesem Objekt interagieren.
Zum Beispiel zwei spezifische Situationen:
1. Wenn es sich bei dem Objekt um ein sehr großes Bild handelt und die Anzeige lange dauert, verwenden Sie ein Zum Öffnen dieses Dokuments muss ein Editor oder Browser verwendet werden. Das Dokument muss sehr schnell geöffnet werden und Sie können nicht darauf warten, dass das große Bild verarbeitet wird. In diesem Fall müssen Sie einen Bild-Proxy erstellen, um das echte Bild zu ersetzen.
2. Wenn sich das Objekt auf einem Remote-Server im Internet befindet, kann der direkte Betrieb des Objekts aufgrund der Netzwerkgeschwindigkeit langsam sein. Dann können wir zuerst Proxy verwenden, um das Objekt zu ersetzen.
Kurz gesagt, das Prinzip ist, dass teure Objekte nur dann erstellt werden sollten, wenn sie verwendet werden. Dieses Prinzip kann uns viel wertvollen Java-Speicher sparen. Daher denken einige Leute, dass Java Ressourcen und Speicher verbraucht. Ich denke, dass dies in gewissem Zusammenhang mit Programmierideen steht.
So verwenden Sie den Proxy-Modus
Nehmen Sie das Jive-Forensystem als Beispiel. Es gibt viele Arten von Benutzern, die auf das Forensystem zugreifen: registrierte normale Benutzer, Forummanager, Systemmanager und Besucher . Nur registrierte normale Benutzer können die Foren verwalten, für die sie autorisiert sind. Diese Berechtigungsaufteilung und -verwaltung erfolgt über Proxy.
Forum ist die Kernschnittstelle von Jive. Die wichtigsten Verhaltensweisen im Zusammenhang mit Forenvorgängen werden im Forum angezeigt, wie z. B. der Name des Forums, das Abrufen und Ändern der Forumsbeschreibung, das Veröffentlichen, Löschen und Bearbeiten von Beiträgen usw.
Benutzer mit verschiedenen Berechtigungsstufen werden in ForumPermissions definiert:
public class ForumPermissions implements Cacheable { /** * Permission to read object. */ public static final int READ = 0; /** * Permission to administer the entire sytem. */ public static final int SYSTEM_ADMIN = 1; /** * Permission to administer a particular forum. */ public static final int FORUM_ADMIN = 2; /** * Permission to administer a particular user. */ public static final int USER_ADMIN = 3; /** * Permission to administer a particular group. */ public static final int GROUP_ADMIN = 4; /** * Permission to moderate threads. */ public static final int MODERATE_THREADS = 5; /** * Permission to create a new thread. */ public static final int CREATE_THREAD = 6; /** * Permission to create a new message. */ public static final int CREATE_MESSAGE = 7; /** * Permission to moderate messages. */ public static final int MODERATE_MESSAGES = 8; ..... public boolean isSystemOrForumAdmin() { return (values[FORUM_ADMIN] || values[SYSTEM_ADMIN]); } ..... }
Daher beziehen sich die verschiedenen Betriebsberechtigungen in Forum auf die durch ForumPermissions definierten Benutzerebenen, da die Schnittstelle Forum-Implementierung: ForumProxy verbindet diese Korrespondenz. Um beispielsweise den Namen des Forums zu ändern, kann ihn nur der Forumadministrator oder Systemadministrator ändern. Der Code lautet wie folgt:
public class ForumProxy implements Forum { private ForumPermissions permissions; private Forum forum; this.authorization = authorization; public ForumProxy(Forum forum, Authorization authorization, ForumPermissions permissions){ this.forum = forum; this.authorization = authorization; this.permissions = permissions; } ..... public void setName(String name) throws UnauthorizedException, ForumAlreadyExistsException{ //只有是系统或论坛管理者才可以修改名称 if (permissions.isSystemOrForumAdmin()) { forum.setName(name); } else { throw new UnauthorizedException(); } } ... }
Und DbForum ist die eigentliche Implementierung des Schnittstellenforums Der Name des Forums als Beispiel:
public class DbForum implements Forum, Cacheable { ... public void setName(String name) throws ForumAlreadyExistsException { .... this.name = name; //这里真正将新名称保存到数据库中 saveToDb(); .... } ... }
Wenn es darum geht, den Forumnamen zu ändern, müssen andere Programme zuerst mit ForumProxy entscheiden, ob es die Berechtigung hat, eine bestimmte Sache zu tun ein wahres „Gateway“ und „Sicherheits-Proxy-System“.
In alltäglichen Anwendungen ist es unvermeidlich, dass das Systemautorisierungs- oder Sicherheitssystem immer involviert ist. Unabhängig davon, ob Sie Proxy bewusst verwenden oder nicht, verwenden Sie Proxy bereits.
Lassen Sie uns weiter ausführlich mit Jive sprechen. Im Folgenden geht es um den Werksmodus.
Wir wissen bereits, dass die Verwendung von ForumProxy den Factory-Modus verwendet. In dieser abstrakten Klasse wird der Aufruf von ForumFactory über die Methode getInstance() implementiert wird hier verwendet (ebenfalls eines der Entwurfsmuster) und getInstance() gibt ForumFactoryProxy zurück.
Warum nicht ForumFactory zurückgeben, sondern die ForumFactory-Implementierung ForumFactoryProxy? Der Grund liegt auf der Hand. Sie müssen einen Proxy verwenden, um festzustellen, ob Sie die Berechtigung zum Erstellen eines Forums haben.
In ForumFactoryProxy sehen wir den Code wie folgt:
public class ForumFactoryProxy extends ForumFactory { protected ForumFactory factory; protected Authorization authorization; protected ForumPermissions permissions; public ForumFactoryProxy(Authorization authorization, ForumFactory factory,ForumPermissions permissions){ this.factory = factory; this.authorization = authorization; this.permissions = permissions; } public Forum createForum(String name, String description) throws UnauthorizedException, ForumAlreadyExistsException{ //只有系统管理者才可以创建forum if (permissions.get(ForumPermissions.SYSTEM_ADMIN)) { Forum newForum = factory.createForum(name, description); return new ForumProxy(newForum, authorization, permissions); } else { throw new UnauthorizedException(); } } }
Die Methode createForum gibt auch ForumProxy zurück. Andere Programme können nur mit Proxy interagieren.
Beachten Sie, dass es hier zwei Proxys gibt: ForumProxy und ForumFactoryProxy. Stellt zwei verschiedene Verantwortlichkeiten dar: die Nutzung des Forums und die Erstellung des Forums. Was die Trennung von Verwendung und Erstellung von Objekten betrifft, so wird auch das Factory-Muster verwendet: zum „Einkapseln“ und „Versenden“. Mit anderen Worten: Die Funktionen sollten möglichst einfach sein, um Wartung und Änderung zu erleichtern.
Die Erstellung und Nutzung anderer Beiträge im Jive-Forensystem basieren alle auf der Idee des Forums.
Oben haben wir besprochen, wie Proxy für den Zugriff auf den Autorisierungsmechanismus verwendet werden kann. Außerdem kann Proxy eine andere Optimierungsmethode namens „Copy-on-Write“ vor Benutzern verbergen. Das Kopieren eines großen und komplexen Objekts ist ein teurer Vorgang. Wenn das Originalobjekt während des Kopiervorgangs nicht geändert wird, ist ein solcher Kopieraufwand unnötig. Verwenden Sie einen Proxy, um diesen Kopiervorgang zu verzögern.
比如:我们有一个很大的Collection,具体如hashtable,有很多客户端会并发同时访问它。其中一个特别的客户端要进行连续的数据获取,此时要求其他客户端不能再向hashtable中增加或删除 东东。
最直接的解决方案是:使用collection的lock,让这特别的客户端获得这个lock,进行连续的数据获取,然后再释放lock。
public void foFetches(Hashtable ht){ synchronized(ht){ //具体的连续数据获取动作.. } }
但是这一办法可能锁住Collection会很长时间,这段时间,其他客户端就不能访问该Collection了。
第二个解决方案是clone这个Collection,然后让连续的数据获取针对clone出来的那个Collection操作。这个方案前提是,这个Collection是可clone的,而且必须有提供深度clone的方法。Hashtable就提供了对自己的clone方法,但不是Key和value对象的clone。
public void foFetches(Hashtable ht){ Hashttable newht=(Hashtable)ht.clone(); }
问题又来了,由于是针对clone出来的对象操作,如果原来的母体被其他客户端操作修改了,那么对clone出来的对象操作就没有意义了。
最后解决方案:我们可以等其他客户端修改完成后再进行clone,也就是说,这个特别的客户端先通过调用一个叫clone的方法来进行一系列数据获取操作。但实际上没有真正的进行对象拷贝,直至有其他客户端修改了这个对象Collection。
使用Proxy实现这个方案,这就是copy-on-write操作。
Proxy应用范围很广,现在流行的分布计算方式RMI和Corba等都是Proxy模式的应用。
更多Java设计模式之代理模式(Proxy模式)介绍相关文章请关注PHP中文网!
相关文章: