Cuando la interfaz del sistema necesita agregar nuevos métodos, realmente lamento no haber aprendido antes los patrones de diseño de Java.

Supongamos que hay una interfaz en el sistema y esta interfaz ha sido implementada por clases de implementación 10. De repente, un día, surge un nuevo requisito y las clases de implementación 5 necesitan implementar el mismo método. Luego agrega la definición de este método a la interfaz y piensa que todo es perfecto.

Después de agregar este método a la interfaz y 5 de las clases de implementación, compílelo. No es bueno, las otras cinco clases de implementación informaron un error y no implementaron el método recién agregado. Debe saber que la definición del método en la interfaz debe implementarse en la clase de implementación y no se compilará sin una.

En este momento, lo que le dijo el senior al comienzo del desarrollo de repente sonó en sus oídos: "La brecha entre estas implementaciones puede volverse cada vez más grande en el futuro, y los métodos pueden agregarse a la interfaz, así que tenga cuidado de dejar huecos".

imagen

¿Qué estás haciendo ahora?

Suponiendo que la interfaz anterior sea así, solo hay dos métodos para comer y beber.

public interface IUser {

    /**
     * 吃饭啊
     */
    void eat();

    /**
     * 喝水啊
     */
    void drink();
}

Ahora hay 5 poderosas clases de implementación y se necesita agregar un método play().

Ahora que este es el caso, lo que debe hacerse ahora.

Rompamos el frasco, vámonos

No importa cuál sea la interfaz o no, qué clase de implementación debe agregarse, simplemente agréguela directamente a esa clase de implementación. La interfaz sigue siendo la misma que antes. Todavía hay solo dos métodos para comer y beber, y el método de reproducción es añadido directamente a 5 en la clase de implementación.

public class UserOne implements IUser{

    @Override
    public void eat() {
        System.out.println("吃饭");
    }

    @Override
    public void drink() {
        System.out.println("喝水");
    }
    
    public void play() {
        System.out.println("玩儿");
    }
}

Aunque se puede realizar, se desvía por completo de la intención original de diseñar la interfaz.Originalmente fue construido como un hotel de cinco estrellas, pero después de que se construyó el primer piso, la parte superior se convirtió en una cabaña con techo de paja.

De ahí en adelante, la interfaz es la interfaz y la clase de implementación es la clase de implementación, básicamente no importa. La flexibilidad surge y puede agregar métodos directamente en cualquier clase de implementación que desee agregar en el futuro.

imagen

¿Puedo agregar otra interfaz?

Todavía es un poco de búsqueda, ¿puedo agregar una nueva interfaz? La interfaz anterior permanece sin cambios y se crea una nueva interfaz. Además de los dos métodos anteriores, el método de reproducción se agrega a esta interfaz.

De esta forma, se crea una interfaz separada para aquellos que necesitan implementar el método de reproducción. Como la siguiente  IUseres la interfaz anterior. IUserExtendLa interfaz se agregó recientemente y se agregó el método play(). La clase de implementación que necesita implementar el método play() se cambió para implementar la nueva IUserExtendinterfaz. Solo se cambiaron algunas relaciones de implementación. Los cambios no son muy grandes, y estoy satisfecho

imagen

Pero los buenos tiempos no duran mucho. Después de unos días, se agregará un nuevo método. Suponiendo que es el de la imagen de arriba  UserOneUserNinese debe agregar el método, ¿qué debo hacer?

imagen

Si Dios me da otra oportunidad

Si Dios me da otra oportunidad de hacerlo de nuevo, me diré a mí mismo: "No te metas, mira el patrón de diseño".

patrón de adaptador

El patrón de adaptador se puede crear mediante la creación de una clase de adaptador que implemente la interfaz y proporcione una implementación predeterminada, y luego la clase de implementación existente puede heredar la clase de adaptador en lugar de implementar directamente la interfaz. De esta forma, no es necesario modificar la clase de implementación existente, sino que solo se necesita implementar el nuevo método en la clase de implementación que necesita anular el nuevo método.

imagen

¿No es necesario agregar un método play()? No hay problema, simplemente agréguelo directamente a la interfaz.

public interface IUser {
    void eat();
    void drink();
    void play();
} 

La clase adaptor es muy importante, es una capa de adaptación intermedia y una clase abstracta. ¿Acaso la clase de implementación no implementaba directamente la clase de interfaz antes, pero ahora la clase de adaptador implementa la clase de interfaz y la clase de implementación extiende la clase de adaptador?

En la clase de adaptador, puede dar a cada método una implementación predeterminada y, por supuesto, no puede hacer nada.

public abstract class UserAdapter implements IUser {
    @Override
    public void eat() {
        // 默认实现
    }

    @Override
    public void drink() {
        // 默认实现
    }

    @Override
    public void play() {
        // 默认实现
    }
}
public class UserNine extends UserAdapter {
    @Override
    public void eat() {
        System.out.println("吃饭");
    }

    @Override
    public void drink() {
        System.out.println("喝水");
    }

    @Override
    public void play() {
        System.out.println("玩儿");
    }
}

public class UserTen extends UserAdapter {
    @Override
    public void eat() {
        System.out.println("吃饭");
    }

    @Override
    public void drink() {
        System.out.println("喝水");
    }
}

Método de llamada:

IUser userNine = new UserNine();
userNine.eat();
userNine.drink();
userNine.play();

IUser userTen = new UserTen();
userTen.eat();
userTen.drink();

De esta manera, agregue métodos a voluntad en la interfaz, luego agregue la implementación predeterminada del método correspondiente en la clase de adaptador y finalmente agregue la implementación personalizada correspondiente en la clase de implementación que necesita implementar el nuevo método.

patrón de estrategia

El patrón de estrategia permite realizar diferentes comportamientos de acuerdo con diferentes estrategias. En este caso, puede definir el nuevo método como una interfaz de estrategia y luego proporcionar una estrategia diferente para cada clase de implementación que necesite implementar el nuevo método.

Cambia la interfaz a una clase abstracta, donde los métodos eat() y drink() permanecen sin cambios, y no puedes hacer nada, y puedes personalizar lo que quieras en la clase de implementación.

El método play() se agregó más tarde, por lo que nos enfocamos en el método play() La estrategia en el modo de estrategia se usa en el método play().

public abstract class AbstractUser {

    IPlayStrategy playStrategy;
  
   public void setPlayStrategy(IPlayStrategy playStrategy){
        this.playStrategy = playStrategy;
    }
  
    public void play(){
        playStrategy.play();
    }

    public void eat() {
        // 默认实现
    }

    public void drink() {
        // 默认实现
    } 
}

IPlayStrategyEs una interfaz de estrategia. El patrón de estrategia es un patrón de comportamiento. Jugar es un tipo de comportamiento. Por supuesto, puede tratar todos los métodos que se agregarán más adelante como comportamientos.

Establecemos una interfaz de estrategia para el comportamiento de "jugar", y luego no importa lo que juegues o cómo juegues, puedes implementar esta  IPlayStrategyinterfaz.

public interface IPlayStrategy {

    void play();
}

Luego, crea dos clases de implementación para realizar dos formas de jugar.

Implementación del primer juego jugable

public class PlayGameStrategy implements IPlayStrategy{

    @Override
    public void play() {
        System.out.println("玩游戏");
    }
}

Segunda implementación de jugar al fútbol

public class PlayFootballStrategy implements IPlayStrategy{
    @Override
    public void play() {
        System.out.println("玩儿足球");
    }
}

Luego define  AbstractUserla subclase

public class UserOne extends AbstractUser{
    @Override
    public void eat() {
        //自定义实现
    }

    @Override
    public void drink() {
        //自定义实现
    }
}

Método de llamada:

public static void main(String[] args) {
  AbstractUser userOne = new UserOne();
  // 玩儿游戏
  userOne.setPlayStrategy(new PlayGameStrategy());
  userOne.play();
  // 玩儿足球
  userOne.setPlayStrategy(new PlayFootballStrategy());
  userOne.play();
}

El diagrama de clase general se ve así:

imagen

por fin

A través del modo de adaptador y el modo de estrategia, podemos asegurarnos de que las clases de implementación específicas implementen una interfaz común o hereden una clase base común y, al mismo tiempo, al agregar nuevas funciones (métodos), podemos asegurarnos de que el diseño sea como claro posible. A diferencia de la forma anterior de romper latas y romper, la interfaz y la clase de implementación están casi fuera de relación.Cada clase de implementación tiene su propio juego.

Supongo que te gusta

Origin blog.csdn.net/Javatutouhouduan/article/details/132061504
Recomendado
Clasificación