Interfaces

Una interface en Java, es un tipo abstracto que se utiliza para definir una interfaz a implementar por las clases. Las interfaces se declaran utilizando la palabra clave interface y conteniendo solamente la firma del método y las declaraciones de las constantes (que pueden ser static y final). Una interfaz no puede contener las definiciones de los métodos.

Las interfaces son implementadas y no pueden ser instanciadas. Una clase que implementa una interfaz debe implementar todos los métodos descritos en la interfaz.

Una ventaja del uso de las interfaces es que simulan la herencia múltiple. Todas las clases en Java tienen solamente una clase base, la única excepción es java.lang.Object (la clase raiz del sistema tipo de Java); la herencia múltiple de clase no está permitida.

Para explicar el concepto de interfaces, vamos a jugar al bingo y para esto vamos a crear 20 tarjetas de bingo, con 15 números en cada una de las tarjetas.

Primero, creamos una clase Main con un new ArrayList de Bingo Cards(tarjetas de bingo). Después de añadir cada una de las tarjetas a la lista, las imprimimos.

package com.edu4java.tutorial16;

import java.util.ArrayList;

public class Main {
public static void main(String[] args) {
	ArrayList<BingoCard> bingoList = new ArrayList<BingoCard>();
	
	for (int i = 0; i < 20; i++) {
		BingoCard bingo=new BingoCard();
		bingoList.add(bingo);
		bingo.syso();
	}
}
}

En la clase "BingoCard", creamos un new array de ints con 15 posiciones. Después de crearlo, se llama al constructor y utilizamos el objeto Random para sortear los números.

Utilizamos un for para iterar sobre el array y en cada bucle, añadimos un número, sorteado entre los números 0 a 99.

Sorteamos los números, los incluimos en el array de ints "bingo", para que estén guardados en una variable de instancia de "BingoCard" y cada vez que se llame al método "syso", llamamos al método "toString()".

El método "toString", itera sobre el array de ints "bingo", concatenando cada uno de ellos con el anterior e imprimiéndolos.

package com.edu4java.tutorial16;

import java.util.Random;

public class BingoCard {
	int[] bingo = new int[15];

	public BingoCard() {
		Random random = new Random();
		for (int i = 0; i < bingo.length; i++) {
			bingo[i] = random.nextInt(100);
		}
	}

	public int[] getBingo() {
		return bingo;
	}

	public void setBingo(int[] bingo) {
		this.bingo = bingo;
	}

	@Override
	public String toString() {
		String s = "[";
		for (int i = 0; i < bingo.length; i++) {
			s = s + bingo[i] + ",";
		}
		return s + "]";

	}

	public void syso() {
		System.out.println(this.toString());
	}

}

El constructor de la clase "BingoCard1" tiene un filtro para evitar los números repetidos en las tarjetas de bingo. Esto es una mejora con respecto a la clase "BingoCard".

package com.edu4java.tutorial16;

import java.util.Random;

public class BingoCard1 {
	int[] bingo = new int[15];

	public BingoCard1() {
		Random random = new Random();
		for (int i = 0; i < bingo.length; i++) {
			bingo[i] = random.nextInt(100);
			if (isRepeated(i)) {
				i--;
			}
		}
	}

	private boolean isRepeated(int i) {
		for (int j = 0; j < i; j++) {
			if (bingo[i] == bingo[j]) {
				return true;
			}
		}
		return false;
	}

	public int[] getBingo() {
		return bingo;
	}

	public void setBingo(int[] bingo) {
		this.bingo = bingo;
	}

	@Override
	public String toString() {
		String s = "[";
		for (int i = 0; i < bingo.length; i++) {
			s = s + bingo[i] + ",";
		}
		return s + "]";

	}

	public void toConsole() {
		System.out.println(this.toString());
	}

}

BingoCard2 tiene otra mejora más; el método printoToConsole(), elimina la coma del final que no quedaba muy bien.

package com.edu4java.tutorial16;

import java.util.Random;

public class BingoCard2 {
	int[] bingo = new int[15];

	public BingoCard2() {
		Random random = new Random();
		for (int i = 0; i < bingo.length; i++) {
			bingo[i] = random.nextInt(100);
		}
	}

	public int[] getBingo() {
		return bingo;
	}

	public void setBingo(int[] bingo) {
		this.bingo = bingo;
	}


	public void printoToConsole() {
		System.out.print("[");
		for (int i = 0; i < bingo.length; i++) {
			System.out.print(bingo[i]);
			if (i + 1 < bingo.length) {
				System.out.print(",");

			}
		}
		System.out.println("]");
	}

}

Cada vez que hacemos una mejora, tenemos que cambiar mucho código en la clase Main. Esto puede ser bastante problemático cuando tenemos miles de clases. Para evitar esto, definimos una interface;

package com.edu4java.tutorial16;

public interface IBingoCard {

	void syso();

}

Y hacemos que todas las clases BingoCard implementen la interfaz IBingoCard y sus métodos;

package com.edu4java.tutorial16;

import java.util.Random;

public class BingoCard implements IBingoCard {
	int[] bingo = new int[15];

	public BingoCard() {
		Random random = new Random();
		for (int i = 0; i < bingo.length; i++) {
			bingo[i] = random.nextInt(100);
		}
	}

	public int[] getBingo() {
		return bingo;
	}

	public void setBingo(int[] bingo) {
		this.bingo = bingo;
	}

	@Override
	public String toString() {
		String s = "[";
		for (int i = 0; i < bingo.length; i++) {
			s = s + bingo[i] + ",";
		}
		return s + "]";

	}

	/* (non-Javadoc)
	 * @see com.edu4java.tutorial16.IBingoCard#syso()
	 */
	@Override
	public void syso() {
		System.out.println(this.toString());
	}

}

package com.edu4java.tutorial16;

import java.util.Random;

public class BingoCard1 implements IBingoCard{
	int[] bingo = new int[15];

	public BingoCard1() {
		Random random = new Random();
		for (int i = 0; i < bingo.length; i++) {
			bingo[i] = random.nextInt(100);
			if (isRepeated(i)) {
				i--;
			}
		}
	}

	private boolean isRepeated(int i) {
		for (int j = 0; j < i; j++) {
			if (bingo[i] == bingo[j]) {
				return true;
			}
		}
		return false;
	}

	public int[] getBingo() {
		return bingo;
	}

	public void setBingo(int[] bingo) {
		this.bingo = bingo;
	}

	@Override
	public String toString() {
		String s = "[";
		for (int i = 0; i < bingo.length; i++) {
			s = s + bingo[i] + ",";
		}
		return s + "]";

	}


	@Override
	public void syso() {
		System.out.println(this.toString());
		
	}

}

package com.edu4java.tutorial16;

import java.util.Random;

public class BingoCard2 implements IBingoCard {
	int[] bingo = new int[15];

	public BingoCard2() {
		Random random = new Random();
		for (int i = 0; i < bingo.length; i++) {
			bingo[i] = random.nextInt(100);
		}
	}

	public int[] getBingo() {
		return bingo;
	}

	public void setBingo(int[] bingo) {
		this.bingo = bingo;
	}

	@Override
	public void syso() {
		System.out.print("[");
		for (int i = 0; i < bingo.length; i++) {
			System.out.print(bingo[i]);
			if (i + 1 < bingo.length) {
				System.out.print(",");

			}
		}
		System.out.println("]");

	}

}

Por último, utilizamos esa interfaz en la clase Main. La podemos usar por ejemplo para probar la clase BingoCard2 y solamente tendremos que modificar la clase Main en un lugar;

package com.edu4java.tutorial16;

import java.util.ArrayList; 

public class Main {
public static void main(String[] args) {
	ArrayList<IBingoCard>  bingoList = new ArrayList<IBingoCard>();
	
	for (int i = 0; i < 20; i++) {
		IBingoCard bingo=new BingoCard2();
		bingoList.add(bingo);
		bingo.syso();
	}
}
}
<< Anterior Siguiente >>