Saltar al contenido

Herencia en java.

La herencia en java es una de las características más importantes de este lenguaje. Forma parte de los cuatro pilares fundamentales junto al encapsulamiento o encapsulación, la abstracción y el polimorfismo.

Que es la herencia en java.

Al igual que en la vida real un padre puede heredar de un hijo, en java es exactamente lo mismo.

Una clase hija puede heredar de una clase padre. En este caso, la clase hija, va a adquirir las características y métodos de la clase padre más los que ella misma pueda tener.

De esta forma, las características y métodos getter y setter que tiene la clase padre, no tendremos que volver a declararlas en la clase hija. Por otro lado, podemos diferenciar dos tipos de clases:

  • Superclase o clase padre. Es la clase de la cual se hereda. Por ejemplo, la clase Object es la clase padre de la que heredan el resto de clases en java. Incluso aquellas que nosotros creamos de forma personalizada.
  • Clase derivada o clase hija. Es aquella que hereda de la clase padre. Además, también puede ser clase padre de otras. Esta clase, no solo heredará las características y propiedades de la clase padre, sino también sus métodos constructores.

Como se declara la herencia en java. Cláusula “extends” y método super();

Para indicar que una clase hereda de otra, usamos la palabra reservada “extends“. Además cuando creamos el método constructor de la clase hija, debemos llamar al constructor de la clase padre. Esto lo haremos a través del método super(). A este método le debemos pasar los parámetros correspondientes si fuese necesario.

Cuantos tipos de herencia existen en java.

En cuanto a la herencia en java, hay que destacar que en este lenguaje, no existe la herencia múltiple.

Java posee un tipo de herencia simple. Esto quiere decir que, una o varias clases, solo y exclusivamente heredan de una única clase. Si por cualquier circunstancia, una clase tiene que heredar de varias clases, debemos hacer uso de las interfaces.

¿Cómo determinar cual es la clase padre y la clase hija?

Cuando trabajamos con la herencia en java, debemos determinar cual será la clase padre o superclase y que clase o clases dependerán de ella. Esto obedece a una regla muy básica y muy sencilla. Esta es la regla de “es un/a?”.

La regla «es un» para comprobar la herencia en java.

Por ejemplo, imaginemos que tenemos dos clases, coches y motos y apliquemos esta regla.

  • ¿Un coche es una moto?
  • ¿Una moto es un coche?

Mas ejemplos serían:

  • ¿Un camión es un coche?
  • ¿Una furgoneta es un coche?
  • ¿Una bicicleta es una moto?
  • ¿Un autobús es un coche?

Evidentemente si nos hacemos estas preguntas, la respuesta es no. Lógicamente todos estos medios de transporte, tienen algo en común, pero todos tienen características diferentes. Imaginaos que tenemos una clase vehículo.

  • ¿Un coche es un vehículo?
  • ¿Una moto es un vehículo?
  • ¿Un camión es un vehículo?
  • ¿Una furgoneta es un vehículo?
  • ¿Una bicicleta es una vehículo?
  • ¿Un autobús es un vehículo?

En este segundo caso, la respuesta es sí. Por lo tanto, la clase vehículo, será la clase padre. Por otro lado las clases coche, moto, camión, furgoneta, bicicleta y autobús, serán clases que heredarán de la clase vehículo.

Vamos a crear un ejemplo de herencia entre una clase persona y una clase socio. Pero antes de ello, veremos lo que es una clase abstracta y que características tiene. Esto lo haremos así ya que una de las clases que crearemos para realizar la herencia, será una clase abstracta.

Que es una clase abstracta.

Es aquella en la que uno o varios métodos deben de ser sobreescritos en las clases hijas.

Por ejemplo, imaginemos que de una clase persona tenemos una característica que es la descripción de la persona.

Además, tenemos objetos de tipo empleados y alumnos. En este caso la descripción de la persona sería diferente. Un alumno estudia, mientras que un empleado cobra un sueldo, por lo tanto, la descripción de los dos sería diferente.

Además debemos tener en cuenta lo siguiente:

  • Cuando declaramos una clase como abstracta, utilizaremos la palabra reservada “abstract
  • Una clase que tenga como mínimo un método abstracto, debe ser declarada como clase abstracta.
  • Una clase abstracta no tiene porque tener métodos abstractos.
  • Los métodos abstractos solo pueden ser declarados pero no pueden llevar código en su interior.
  • No se pueden crear objetos de la clase abstracta, pero si de las subclases, siempre y cuando éstas no sean de tipo abstracto.

Ejemplo de herencia en java.

Para este ejemplo, vamos a crear dos clases.

  • Una que será clase persona
  • Y otra que será clase socio.

Ahora vamos a pensar en el socio y vamos a intentar crear una herencia. Imaginemos una clase persona.

  • ¿Un socio en una persona? La respuesta es si.
  • ¿Una persona es un socio? Unos pueden pensar que si, otros pueden pensar que no… ¿y tú que opinas?

En teoría si, claro que una persona es un socio,… pero una persona no necesariamente tiene porque ser solamente un socio.

También hay estudiantes, trabajadores, mecánicos, informáticos, etc. Esto nos lleva a la conclusión de que la clase persona está por encima de la clase socio. Por este motivo, socio heredará de persona. O lo que es lo mismo, persona es la clase padre y socio la clase hija.

Teniendo en cuenta esto, vamos a crear una clase persona que tendrá como características un dni, un nombre y unos apellidos. Como toda clase, si tiene unas características, tendrá unos comportamientos, es decir, unos métodos get y set.

Ejemplo de creación de superclase o clase padre.

package objetos;
/* En este caso estamos creando una clase abstracta
 * ya que habrá un método que sea abstracto y por lo tanto
 * al haber un método abstracto, la clase persona debe ser abstracta*/
public abstract class Persona {
	
	// Creamos las características de los socios
	private String dni; // Atributo dni
	private String nombre; // Atributo nombre
	private String apellidos; // Atributo apellidos
	
	// Creamos un constructor que nos pida todos los parámetros
	Persona(String dniSocio, String nombreSocio, String apellidosSocio){
		
		this.dni = dniSocio;
		this.nombre = nombreSocio;
		this.apellidos = apellidosSocio;	
	}
	
	// Creamos un segundo constructor que solo pida el dni.
	Persona(String dniSocio){
		
		this.dni =dniSocio;
		this.nombre ="";
		this.apellidos ="";
	}
	public String getDni() {
		return dni;
	}
	public void setDni(String dni) {
		this.dni = dni;
	}
	public String getNombre() {
		return nombre;
	}
	public void setNombre(String nombre) {
		this.nombre = nombre;
	}
	public String getApellidos() {
		return apellidos;
	}
	public void setApellidos(String apellidos) {
		this.apellidos = apellidos;
	}
	public abstract String toString();
}

Una vez ya hemos creado la clase persona, la cual hemos creado como abstracta, vamos a ver como quedaría entonces la clase socio, la cual en este caso heredará de la clase persona.

Uso de extends y super(). Creando la herencia entre clases.

package objetos;
/* En este caso utilizamos la palabra reservada extends
 * para indicar que la clase Socio, hereda de la clase Persona*/
public class Socio extends Persona {
	/* Creamos un atributo para el socio. Este atributo será
	 * accesible sólo desde esta clase.*/
	private int idSocio;
	
	/* Creamos un constructor y le pasamos por parámetros
	 * los datos del socio*/
	Socio(String dniSocio, String nombreSocio,
			String apellidosSocio, int id){
		
		/* Llamamos al método super y le pasamos por parámetro
		 * los argumentos que pide la clase padre llamada persona*/
		super(dniSocio, nombreSocio, apellidosSocio);
		this.idSocio=id;
	}
	
	/* Creamos un segundo constructor que solo pida el dni.
	 * y el número de socio*/
	Socio(String dniSocio, int id){
		
		/* Llamamos al constructor de la clase padre, este constructor
		 * padre recibe un parámetro que le pasamos en el método super.*/
		super(dniSocio);
		this.idSocio=id;
	}
	
	/* En este casso este método toString está sobreescribiendo
	 * al método toString de la clase padre (la clase persona).
	 * esto es posible ya que hemos declarado el método toString
	 * como abstracto dentro de la clase persona. Además al declarar
	 * un método como abstracto en una clase padré o superclase,
	 * estamos obligados a sobreescribir el método en las subclases*/
	public String toString() {
		
		return "Se ha registrado un nuevo socio "
				+ "con el número " + idSocio + ".";	
	}
}

Creación de objetos de tipo socio desde el método main.

Recordamos que la clase persona al ser una clase abstracta, no podemos crear objetos de ella, pero si podemos hacerlo de la clase socio, ya que esta hereda de ella. Por este motivo en el método main, solo podemos declarar objetos de tipo socio. En este ejemplo construiremos un objeto de tipo socio y mostraremos por pantalla sus datos a través del método abstracto toString().

package objetos;
public class Principal {
	
	public static void main(String[] args) {
		
		/* Creamos un objeto de tipo Socio pasandole los parámentros
		 * dni, nombre y apellidos y el número de socio.*/
		Socio primerSocio =new Socio("12345678H","Antonio","Martínez",354);
		
		/* Mostramos los datos del socio por pantalla*/
		System.out.println(primerSocio.toString());
	}
}