23 Patrones de diseño Capítulo 16: Patrón de visitantes de Java
Definición: Encapsula ciertas operaciones que actúan en cada elemento en una determinada estructura de datos. Puede definir nuevas operaciones que actúen sobre estos elementos sin cambiar la estructura de datos.
Tipo: Patrón de comportamiento
Diagrama de clases:
El modo de visitante puede ser el modo más complejo entre los modos de comportamiento, pero esta no puede ser una razón por la que no lo dominemos.
Veamos primero un simple ejemplo, el código es el siguiente
clase A {public void Method1 () {System.out.println ("I Am A"); } Public void Method2 (b b) {B.Showa (this); }} clase B {public void showa (a a) {a.method1 (); }}Veamos principalmente cuál es la diferencia entre el método método1 y el método del método2 en la clase A. El método Method1 es muy simple, simplemente imprima una oración "I Am A"; Método Method2 es un poco más complicado, use la clase B como parámetro y llame al método showa de la clase B.
Echemos un vistazo al método showa de la clase B. El método showA utiliza la clase A como parámetro, y luego llama al método1 del método de clase A. Puede ver que el método Method2 solo está llamando a su propio método Method1. Su resultado de ejecución también debería ser "Yo soy un". Después del análisis, ejecutemos estos dos métodos y ver el resultado de la ejecución:
prueba de clase pública {public static void main (string [] args) {a a = new a (); a.method1 (); a.method2 (nuevo B ()); }}El resultado de la ejecución es:
Soy un
Soy un
Después de comprender este ejemplo, comprenderá el 90% del patrón de visitantes. En el ejemplo, para la clase A, la clase B es un visitante. Sin embargo, este ejemplo no es todo el modo de visitante. Aunque es intuitivo, tiene poca escalabilidad. Hablemos sobre la implementación general del modo de visitante. Puede ver a través del diagrama de clases que en el modo de visitante, los siguientes roles se incluyen principalmente:
Visitante abstracto: una clase o interfaz abstracta que declara qué elementos puede acceder al visitante. Específicamente en el programa, los parámetros en el método de visita definen a qué objetos se puede acceder.
Visitante: Implemente el método declarado por los visitantes abstractos, que afecta lo que los visitantes deben hacer y lo que deben hacer después de acceder a una clase.
Clase de elementos abstractos: una interfaz o clase abstracta que declara qué tipo de acceso de visitante se acepta. El programa se define a través de parámetros en el método de aceptación. En general, hay dos tipos de métodos para elementos abstractos, uno es su propia lógica comercial, y el otro es a qué tipo de visitantes pueden acceder.
Clase de elementos: implementa el método de aceptación declarado por la clase de elementos abstractos, generalmente visitante. Visit (esto), y básicamente ha formado una fórmula fija.
Objeto estructural: un contenedor de elementos generalmente contiene un contenedor que acomoda múltiples clases e interfaces diferentes, como List, Set, Map, etc. Este rol rara vez se abstrae en el proyecto.
Implementación del código común del modo visitante
Elemento de clase abstracta {public abstract void Acept (visitante ivisitor); Public Abstract void dosomething (); } interfaz ivisitor {public void visit (concreteelement1 el1); visita pública vacía (concreteelement2 El2); } class ConcreteElement1 extiende el elemento {public void dosomething () {System.out.println ("Este es elemento 1"); } public void Acept (visitante ivisitor) {visiter.visit (this); }} class ConcreteElement2 extiende el elemento {public void dosomething () {System.out.println ("Esto es elemento 2"); } public void Acept (visitante ivisitor) {visiter.visit (this); }} El visitante de clase implementa ivisitor {public void visit (concreteelement1 el1) {el1.dosomthething (); } visita pública nula (concreteelement2 el2) {el2.dosomthething (); }} class ObjectStruture {public static list <Elemement> getList () {list <emement> list = new ArrayList <ememement> (); Rand aleatory = new Random (); for (int i = 0; i <10; i ++) {int a = ran.nextint (100); if (a> 50) {list.Add (new ConcreteElement1 ()); } else {list.add (nuevo concreteElement2 ()); }} lista de retorno; }} Cliente de clase pública {public static void main (string [] args) {list <emement> list = objectStruture.getList (); for (elemento e: list) {e.accept (nuevo visitante ()); }}} Ventajas del modo visitante
Realice el principio de responsabilidad única: en cualquier escenario en el que el modo de visitante sea aplicable, las operaciones que deben encapsularse en el visitante en la clase de elementos deben ser operaciones que tengan poco que ver con la clase de elementos en sí y son volátiles. Por un lado, el uso del modo de visitante cumple con el principio de responsabilidad única y, por otro lado, porque las operaciones encapsuladas suelen ser volátiles, cuando ocurren cambios, la expansión de la parte cambiante se puede lograr sin cambiar la clase de elementos en sí.
Buena escalabilidad: las clases de elementos pueden extender diferentes operaciones al aceptar diferentes visitantes.
Escenarios aplicables para el modo de visitante
Si hay algunas operaciones en un objeto que no están relacionados con el objeto (o débilmente relacionados) y para evitar estas operaciones que contaminan el objeto, puede usar el modo de visitante para encapsular estas operaciones en el visitante.
Si hay operaciones similares en un grupo de objetos, para evitar una gran cantidad de código duplicado, estas operaciones duplicadas también pueden encapsularse en el visitante.
Sin embargo, el modo de visitante no es tan perfecto, y también tiene defectos fatales: agregar nuevas clases de elementos es más difícil. A través del código del patrón de visitantes, podemos ver que en la clase de visitantes, cada clase de elementos tiene su método de procesamiento correspondiente. Es decir, cada clase de elementos debe agregarse para modificar la clase de visitantes (también incluida la clase de subclase o implementación de la clase de visitantes), que es bastante problemático de modificar. Es decir, cuando el número de clases de elementos es incierto, el modo de visitante debe usarse con precaución. Por lo tanto, el modo de visitante es más adecuado para refactorizar las funciones existentes. Por ejemplo, si se han determinado las funciones básicas de un proyecto, los datos de las clases de elementos se han determinado básicamente y no cambiarán. Todo lo que cambiará son las operaciones relevantes dentro de estos elementos. En este momento, podemos usar el modo de visitante para refactorizar el código original, para que las funciones originales puedan modificarse sin modificar cada clase de elemento.
Resumir
Como GOF, el autor del patrón de diseño, describe el modo de visitante: en la mayoría de los casos, debe usar el modo de visitante, pero una vez que lo necesita, realmente lo necesita. Por supuesto, esto es solo para los verdaderos grandes. En realidad (al menos en el entorno en el que estoy), muchas personas a menudo son adictas a los patrones de diseño. Al usar un patrón de diseño, nunca consideran seriamente si el patrón que están utilizando es adecuado para este escenario, pero a menudo solo quieren mostrar su capacidad para controlar el diseño orientado a objetos. Si tiene esta mentalidad al programar, a menudo abusa del patrón de diseño. Por lo tanto, al aprender patrones de diseño, debe comprender la aplicabilidad de los patrones. Es necesario usar un patrón porque comprende sus ventajas, no usar un patrón porque comprende sus desventajas; En lugar de usar un patrón porque no comprende sus desventajas, no usar un patrón porque no comprende sus ventajas.
Lo anterior es todo el contenido de este artículo. Espero que sea útil para el aprendizaje de todos y espero que todos apoyen más a Wulin.com.