2017-02-12 1 views
3

Ma question est lambda et les références de méthodes concernent toutes les interfaces fonctionnelles. ils n'en fournissent que la mise en œuvre.java 8 référence de la méthode derrière la scène

maintenant Quand j'écris:

class Apple{ 
private int weight; 
private String color; 

public String getColor() { 
    return color; 
} 

public void setColor(String color) { 
    this.color = color; 
} 

public int getWeight() { 
    return weight; 
} 

public void setWeight(int weight) { 
    this.weight = weight; 
}} 

et si j'écris:

  Function<Apple, Integer> getWeight = Apple::getWeight; 

ou

 appleList.stream().map(Apple::getColor).collect(toList()); 

comment il travaille effectivement mon getter ne prend aucun paramètre d'Apple ? car selon l'interface fonctionnelle de la fonction

@FunctionalInterface 
public interface Function<T, R> { 
R apply(T t);} 

il attend un paramètre et retourner quelque chose et il devrait fonctionner effectivement lorsque le getter est comme:

public int getWeight(Apple a) { 
    return a.weight; 
} 

je suis peu confus merci à l'avance

Répondre

3

Un tel Function<Apple, Integer> ne doit pas être confondu avec une instance d'un Apple.

Rappelez-vous les fonctions de l'école?
Vous devez prendre un élément du domaine (ici une pomme de Apple s) et il sera apparié à exactement un élément correspondant de codomain (ici un entier de Integer s). Function lui-même n'est attribué à aucune pomme particulière.

Vous pouvez l'utiliser de cette façon:

List<Apple> apples = new ArrayList<Apple>(); 
apples.add(new Apple(120, "red")); 
apples.add(new Apple(150, "green")); 
apples.add(new Apple(150, "yellow")); 
List<String> colors = apples.stream() 
          .map(Apple::getColor) 
          .collect(Collectors.toList()); 
System.out.println(colors); 

Apple::getColor est équivalent à un Function<Apple, String>, qui renvoie la couleur de chaque pomme:

Function<Apple, Integer> getColor = new Function<Apple, Integer>() { 
    @Override 
    public Integer apply(Apple apple) { 
     return apple.getColor(); 
    } 
}; 

De plus

List<String> colors = apples.stream() 
          .map(Apple::getColor) 
          .collect(Collectors.toList()); 

est équivalent à :

List<String> colors = apples.stream() 
          .map(apple -> apple.getColor()) 
          .collect(Collectors.toList()); 
3

Cela est décrit clairement dans le tutoriel Method reference comme référence à une méthode d'instance d'un objet arbitraire d'un type particulier. Comme l'objet a le type du type de méthode de référence, alors l'objet sera celui sur lequel la méthode sera appelée. Signifie que:

map(Apple::getColor) 

équivaut à:

map(a -> a.getColor())