Al usar una clase abstracta para implementar una interfaz, sucede algo curioso en Java: algunos de los métodos de la interfaz pueden faltar por completo (es decir, no hay una declaración abstracta o una implementación real), pero el compilador no se queja.
Por ejemplo, dada la interfaz:
public interface IAnything {
void m1();
void m2();
void m3();
}
la siguiente clase abstracta se compila alegremente sin advertencia o error:
public abstract class AbstractThing implements IAnything {
public void m1() {}
public void m3() {}
}
¿Puedes explicar porque?
java
interface
abstract-class
Giulio Piancastelli
fuente
fuente
:w
uno de los archivos.Respuestas:
Esto se debe a que si una clase es abstracta, entonces, por definición, debe crear subclases para crear una instancia. Se requerirán las subclases (por parte del compilador) para implementar cualquier método de interfaz que la clase abstracta haya omitido.
Siguiendo su código de ejemplo, intente hacer una subclase de
AbstractThing
sin implementar elm2
método y vea qué errores le da el compilador. Te obligará a implementar este método.fuente
Perfectamente bien.
No puede crear instancias de clases abstractas ... pero las clases abstractas pueden usarse para albergar implementaciones comunes para m1 () y m3 ().
Entonces, si la implementación m2 () es diferente para cada implementación pero m1 y m3 no lo son. Puede crear diferentes implementaciones concretas de IAnything con solo la implementación de m2 diferentes y derivar de AbstractThing, respetando el principio DRY. Validar si la interfaz está completamente implementada para una clase abstracta es inútil.
Actualización : Curiosamente, encuentro que C # impone esto como un error de compilación. En este escenario, se ve obligado a copiar las firmas del método y agregarles el prefijo 'public abstract' en la clase base abstracta ... (algo nuevo todos los días :)
fuente
Esta bien. Para comprender lo anterior, primero debe comprender la naturaleza de las clases abstractas. Son similares a las interfaces a ese respecto. Esto es lo que Oracle dice sobre esto aquí .
Por lo tanto, debe pensar en lo que sucede cuando una interfaz extiende otra interfaz. Por ejemplo ...
... como puede ver, esto también se compila perfectamente bien. Simplemente porque, al igual que una clase abstracta, una interfaz NO puede ser instanciada. Por lo tanto, no es necesario mencionar explícitamente los métodos de su "padre". Sin embargo, TODAS las firmas del método padre se convierten implícitamente en parte de la interfaz extendida o la implementación de la clase abstracta. Por lo tanto, una vez que una clase adecuada (una que se puede instanciar) extiende lo anterior, será necesario asegurarse de que se implemente cada método abstracto.
Espero que ayude ... y Allahu 'alam!
fuente
Interfaz significa una clase que no tiene implementación de su método, pero solo con una declaración.
Por otro lado, la clase abstracta es una clase que puede tener implementación de algún método junto con algún método con solo declaración, sin implementación.
Cuando implementamos una interfaz para una clase abstracta, significa que la clase abstracta heredó todos los métodos de la interfaz. Como, no es importante implementar todo el método en la clase abstracta, sin embargo, se trata de la clase abstracta (también por herencia), por lo que la clase abstracta puede dejar parte del método en la interfaz sin implementación aquí. Pero, cuando esta clase abstracta sea heredada por alguna clase concreta, deben implementar todos los métodos no implementados en la clase abstracta.
fuente
Dada la interfaz:
Así es como Java lo ve realmente:
Por lo tanto, puede dejar algunos (o todos) de estos
abstract
métodos sin implementar, tal como lo haría en el caso de lasabstract
clases que extienden otraabstract
clase.Cuando
implement
unainterface
, la regla de que todos losinterface
métodos deben ser implementadas en la derivadaclass
, sólo se aplica al hormigónclass
aplicación (es decir, que no esabstract
en sí mismo).Si de hecho planea crear un
abstract class
fuera de él, entonces no hay una regla que diga que tieneimplement
todos losinterface
métodos (tenga en cuenta que en tal caso es obligatorio declarar el derivadoclass
comoabstract
)fuente
javap IAnything.class
para generar el segundo fragmento de código.Referencia: http://docs.oracle.com/javase/tutorial/java/IandI/abstract.html
fuente
No se requieren clases abstractas para implementar los métodos. Entonces, aunque implemente una interfaz, los métodos abstractos de la interfaz pueden seguir siendo abstractos. Si intenta implementar una interfaz en una clase concreta (es decir, no abstracta) y no implementa los métodos abstractos, el compilador le dirá: Implemente los métodos abstractos o declare la clase como abstracta.
fuente