No entiendo una cosa, ¿el tipo de referencia del método no debería ser una interfaz funcional? Entonces, ¿cómo pasamos System.out::println como parámetro a forEach? en el siguiente código:
1-¿System.out::println es un consumidor?
2-En caso afirmativo, ¿cuál es su tipo genérico? No me refiero al tipo de lista que está llamando al método, sino al tipo genérico de la referencia del método que pasó a forEach.
Consumer<Integer> consumer=System.out::println; numbers.forEach(consumer);El tipo de System.out.println no es una interfaz funcional, ya que System.out.println es un método, no una interfaz.
Sin embargo, la referencia al método System.out::println puede usarse como una implementación de una interfaz funcional. Dado que println acepta un argumento y no devuelve nada, puede decir que "consume" el argumento que le pasa. Por lo tanto, encaja como una implementación de la interfaz funcional Consumer<T> .
Tenga en cuenta que hay múltiples variantes de println , que se pueden usar para implementar diferentes interfaces funcionales.
Por ejemplo:
Una referencia de método a public void println(int x) puede implementar IntConsumer .
Una referencia de método a public void println(double x) puede implementar DoubleConsumer .
Una referencia de método a public void println(Object x) puede implementar Consumer<T> .
Esta parte del código:
Consumer<Integer> consumer=System.out::println;es igual a esta expresión lambda:
Consumer<Integer> consumer=i->System.out.println(i);y el bloque de código anterior podría escribirse de esta manera como una clase interna anónima utilizando la interfaz de consumidor:
Consumer<Integer> consumer=new Consumer<Integer>(){ public void accept(Integer i){ System.out.println(i); } }Entonces, "System.out.println" en sí mismo no es una interfaz funcional, pero cuando usa :: implementa implícitamente la interfaz Consumer.