Ruby tiene interfaces como cualquier otro idioma.
Tenga en cuenta que debe tener cuidado de no confundir el concepto de Interfaz , que es una especificación abstracta de las responsabilidades, garantías y protocolos de una unidad, con el concepto de interfaceque es una palabra clave en la programación Java, C # y VB.NET. Idiomas En Ruby, usamos el primero todo el tiempo, pero el segundo simplemente no existe.
Es muy importante distinguir los dos. Lo importante es la interfaz , no el interface. No interfacete dice prácticamente nada útil. Nada demuestra esto mejor que las interfaces de marcador en Java, que son interfaces que no tienen miembros en absoluto: solo eche un vistazo a java.io.Serializabley java.lang.Cloneable; esos dos interfacesignifican cosas muy diferentes, pero tienen exactamente la misma firma.
Entonces, si dos interfaces que significan cosas diferentes, tienen la misma firma, ¿ qué es exactamente lo queinterface te garantiza?
Otro buen ejemplo:
package java.util;
interface List<E> implements Collection<E>, Iterable<E> {
void add(int index, E element)
throws UnsupportedOperationException, ClassCastException,
NullPointerException, IllegalArgumentException,
IndexOutOfBoundsException;
}
¿Cuál es la interfaz de java.util.List<E>.add?
- que la duración de la colección no disminuya
- que todos los elementos que estaban en la colección antes todavía están allí
- que
elementesta en la coleccion
¿Y cuál de ellos aparece realmente en el interface? ¡Ninguna! No hay nada en el interfaceque diga que el Addmétodo deba agregar nada, también podría eliminar un elemento de la colección.
Esta es una implementación perfectamente válida de eso interface:
class MyCollection<E> implements java.util.List<E> {
void add(int index, E element)
throws UnsupportedOperationException, ClassCastException,
NullPointerException, IllegalArgumentException,
IndexOutOfBoundsException {
remove(element);
}
}
Otro ejemplo: ¿en java.util.Set<E>qué lugar dice realmente que es, ya sabes, un conjunto ? ¡En ninguna parte! O más precisamente, en la documentación. En inglés.
En casi todos los casos interfaces, tanto de Java como de .NET, toda la información relevante está realmente en los documentos, no en los tipos. Entonces, si los tipos no te dicen nada interesante de todos modos, ¿por qué conservarlos? ¿Por qué no ceñirse solo a la documentación? Y eso es exactamente lo que hace Ruby.
Tenga en cuenta que hay otros idiomas en los que la interfaz se puede describir de manera significativa. Sin embargo, esos lenguajes normalmente no llaman a la construcción que describe la interfaz " interface", la llaman type. En un lenguaje de programación de tipo dependiente, puede, por ejemplo, expresar las propiedades de que una sortfunción devuelve una colección de la misma longitud que el original, que cada elemento que está en el original también está en la colección ordenada y que ningún elemento más grande aparece antes de un elemento más pequeño.
Entonces, en resumen: Ruby no tiene un equivalente a Java interface. Se hace , sin embargo, tiene un equivalente a una aplicación Java de interfaz , y es exactamente el mismo que en Java: documentación.
Además, al igual que en Java, las pruebas de aceptación también se pueden utilizar para especificar interfaces .
En particular, en Ruby, la interfaz de un objeto está determinada por lo que puede hacer , no por lo classque es ni por lo que modulese mezcla. Se puede agregar cualquier objeto que tenga un <<método. Esto es muy útil en las pruebas unitarias, donde se puede simplemente pasar en una Arrayo Stringen lugar de una más complicada Logger, a pesar de que Arrayy Loggerno compartir una explícita interfaceaparte del hecho de que ambos tienen un método llamado <<.
Otro ejemplo es StringIO, que implementa la misma de interfaz como IOy por lo tanto una gran parte de la interfaz de File, pero sin compartir ninguna antepasado común además Object.