Información adicional sobre programación orientada a interfaz
}
Como se muestra en la Figura 1, tanto SolarPoweredMotor como BatteryPoweredMotor se derivan de la clase abstracta Motor. En todo el software, más del 90% del código trata a todos los motores de la misma manera. Ocasionalmente, es necesario verificar si el motor funciona con luz o electricidad. Esto se implementa usando instancia de. El código es el siguiente:
Código
if (instancia de SolarPoweredMotor){. ..}
if (instanceof BatteryPoweredMotor){...}
No importa qué tipo de motor sea, el parámetro de potencia es muy importante, por lo que en todas las clases abstractas derivadas ( SolarPoweredMotor y BatteryPoweredMotor), el método getHorsepower() es eficiente.
El departamento comercial cuenta con un nuevo motor, que es un motor de doble propulsión, tanto eléctrico como ligero. El comportamiento en sí de la propulsión óptica y eléctrica permanece sin cambios, pero el nuevo motor admite ambos comportamientos simultáneamente. Al considerar cómo definir un nuevo tipo de motor de accionamiento fotoeléctrico, comienza a aparecer la diferencia entre interfaces y clases abstractas. El nuevo objetivo es agregar nuevos motores con la menor cantidad de cambios de código posible. Debido a que el código relacionado con el motor de unidad óptica y el motor de unidad eléctrica se ha probado completamente, no se conocen errores. Para agregar un motor de propulsión fotoeléctrica, se debe definir una nueva clase abstracta SolarBatteryPowered. Si SolarBatteryPowered se deriva de la clase abstracta Motor, SolarBatteryPowered no admitirá operaciones de instancia para motores ligeros y eléctricos. En otras palabras, si pregunta si un motor fotoeléctrico funciona con luz o electricidad, la respuesta que obtiene es: ninguna de las dos.
Si SolarBatteryPowered se deriva de la clase abstracta SolarPoweredMotor (o BatteryPoweredMotor), se producirán problemas similares. SolarBatteryPowered no admitirá la operación de instancia para BatteryPoweredMotor (o SolarPoweredMotor). Desde un punto de vista del comportamiento, el motor de accionamiento fotoeléctrico debe derivarse de dos clases abstractas al mismo tiempo, pero el lenguaje Java no permite la herencia múltiple. La razón fundamental por la que surge este problema es que usar clases abstractas significa no sólo definir un comportamiento específico, sino también definir el patrón de implementación. Es decir, se debe definir un modelo de cómo un motor adquiere su comportamiento, en lugar de simplemente afirmar que el motor tiene un determinado comportamiento.
Establecimiento de modelos de comportamiento a través de interfaces
Si utiliza interfaces para establecer modelos de comportamiento, puede evitar especificar implícitamente el modo de implementación. Por ejemplo, los comportamientos anteriores se definen de la siguiente manera utilizando interfaces.
Comportamiento 1:
Código
interfaz pública Motor(){
public int getHorsepower();
}
Comportamiento 2:
Código
interfaz pública BatteryPoweredMotor extiende Motor(){
public int getTimeToRecharge(); p> p>
}
Comportamiento 3:
Código
interfaz pública SolarPoweredMotor extiende Motor{
abstract public int getLumensToOperate () ;
}
El motor fotoeléctrico se puede describir como:
Código
público DualPoweredMotor implementa SolarPoweredMotor, BatteryPoweredMotor{ }
DualPoweredMotor solo hereda la definición de comportamiento, no el modo de implementación del comportamiento, como se muestra en la Figura 2.
Aún puedes usar clases abstractas mientras usas interfaces, pero en este momento la función de las clases abstractas es implementar el comportamiento en lugar de definir el comportamiento. Siempre que la clase que implementa el comportamiento se ajuste a la definición de la interfaz, incluso si cambia la clase abstracta principal, no necesita cambiar la forma en que otro código interactúa con ella. Especialmente para el código de implementación común, las clases abstractas tienen sus ventajas. Las clases abstractas pueden garantizar la relación jerárquica de implementación y evitar la duplicación de código. Sin embargo, incluso cuando utilice clases abstractas, no ignore el principio de definir modelos de comportamiento a través de interfaces. Desde un punto de vista práctico, depender de clases abstractas para definir el comportamiento a menudo conduce a relaciones de herencia demasiado complejas. Sin embargo, definir el comportamiento a través de interfaces puede separar de manera más efectiva el comportamiento y la implementación, lo que facilita el mantenimiento y la modificación del código.
Aprendiendo las características de la interfaz Java
Cuando ves interfaces en Java, lo primero que te viene a la mente puede ser la herencia múltiple en C y otra palabra clave abstracta en Java. Implementar la herencia múltiple desde otra perspectiva es una de las funciones de las interfaces. La existencia de interfaces permite que los objetos en Java se transformen en múltiples tipos base y, al igual que las clases abstractas, puede evitar que otros creen objetos de esta clase porque las interfaces no lo hacen. permitirlo. Crear objetos.
La palabra clave interface se utiliza para declarar una interfaz, que puede generar una clase completamente abstracta y no proporciona ninguna implementación concreta. Las características de la interfaz se resumen a continuación:
1. Los métodos en las interfaces pueden tener listas de parámetros y tipos de retorno, pero no pueden tener ningún cuerpo de método.
2. Las interfaces pueden contener campos, pero se declararán implícitamente estáticas y finales.
3. Los campos de la interfaz solo se almacenan en el área de almacenamiento estático de la interfaz y no pertenecen a la interfaz.
4. Los métodos en la interfaz pueden declararse como públicos o no, pero los resultados se procesarán según el tipo público.
5. Al implementar una interfaz, el método definido debe declararse como tipo público; de lo contrario, será el tipo de acceso predeterminado. El compilador de Java no lo permite.
6. Si no se implementan todos los métodos en la interfaz, la interfaz aún se crea.
7. Para extender una interfaz para generar una nueva interfaz, use la palabra clave extends y para implementar una interfaz, use implements.
La interfaz es similar a la abstracta en algunos lugares, pero la forma de declarar una clase se refiere principalmente a los dos puntos siguientes:
1. definición y variables miembro de la clase base, entonces debe elegir la interfaz en lugar de la clase abstracta.
2. Si sabes que una clase debe ser una clase base, entonces la primera opción debería ser convertirla en una interfaz. Sólo cuando las definiciones de métodos y las variables miembro sean necesarias, se debe elegir el tipo de abstracción. Debido a que en una clase abstracta se permiten uno o más métodos implementados concretamente, mientras no se implementen todos los métodos, la clase seguirá siendo una clase abstracta.
Las anteriores son las características básicas y los campos de aplicación de las interfaces, pero las interfaces no son solo eso. En la estructura de sintaxis de Java, las interfaces pueden estar anidadas, ya sea por una determinada clase o por una interfaz anidada. . Puede que esto no se use mucho en el desarrollo real, pero también es una de sus características. Cabe señalar que al implementar una interfaz, no es necesario implementar ninguna interfaz anidada dentro de ella, y la interfaz privada no se puede implementar fuera de la clase en la que está definida.