Categorías
Java Java 8 Stream

¿Por qué se compila Stream.max (Integer :: max)?

Considere el siguiente código:

Stream<Integer> stream = Stream.of(1,2,3,4);
int max = stream.max(Math::max).get();
System.out.println(max);

Según el Javadoc de Steam.max (), el argumento del método max () debería ser un Comparador. En el código anterior, la referencia del método es a métodos estáticos de la clase Math. Pero el código se compila sin ningún mensaje de advertencia o error.

Entonces, ¿por qué es Math::max aceptable mientras que aparentemente no es un Comparador?

La razón por la que se compila el código anterior está en el modo en que funciona la nueva funcionalidad lambda en Java 8. Se basa en un concepto que se conoce informalmente como interfaces de «método abstracto único (SAM)». La idea básica es que cualquier interfaz con un método abstracto puede ser implementada automáticamente por cualquier referencia de método o lambda, si la referencia de método o lambda coincide con el SAM en la interfaz.

Si echamos un vistazo a la interfaz de funciones Comparator[1], su método abstracto único se parece a lo siguiente:

public Comparator<T> { 
       int compare(T o1, T o2); 
}

Si un método (max () en este caso) está buscando un Comparador, entonces está esencialmente buscando esta firma:

int xxx(Integer o1, Integer o2);

«xxx» significa que el nombre del método no se utiliza con fines de coincidencia. El método Math.max () tiene la siguiente firma:

  Ejemplo de inyección de dependencia de Java
int max(int i1, int i2);

Autoboxing permite que esto aparezca como un comparador en un contexto de método. Por lo tanto, Math::max es aceptado. Del mismo modo, también es aceptable un montón de otros métodos, como Integer::max, Integer::min, Math::minetc.

El resultado será incorrecto. En lugar de, Integer::comparedebe usarse como el siguiente:

max = stream.max(Integer::compare).get();
System.out.println(max);

Referencias:
[1]. Javadoc de Comparator en Java 8
[2]. Esta pregunta también es publicada por Fge de Desbordamiento de pila. La respuesta más popular es publicada por David Lloyd.

Por Programación.Click

Más de 20 años programando en diferentes lenguajes de programación. Apasionado del code clean y el terminar lo que se empieza. ¿Programamos de verdad?

Deja una respuesta

Tu dirección de correo electrónico no será publicada. Los campos obligatorios están marcados con *