Supposons que vous ayez le code suivant:
import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;
public class Test {
public static void main(String[] s) {
Map<String, Boolean> whoLetDogsOut = new ConcurrentHashMap<>();
whoLetDogsOut.computeIfAbsent("snoop", k -> f(k));
whoLetDogsOut.computeIfAbsent("snoop", k -> f(k));
}
static boolean f(String s) {
System.out.println("creating a value for \""+s+'"');
return s.isEmpty();
}
}
Ensuite, vous verrez le message creating a value for "snoop"
exactement une fois, car lors de la deuxième invocation, computeIfAbsent
il y a déjà une valeur pour cette clé. Le k
dans l'expression lambda k -> f(k)
est juste un emplacement (paramètre) pour la clé que la carte passera à votre lambda pour calculer la valeur. Ainsi, dans l'exemple, la clé est transmise à l'appel de la fonction.
Vous pouvez également écrire: whoLetDogsOut.computeIfAbsent("snoop", k -> k.isEmpty());
pour obtenir le même résultat sans méthode d'assistance (mais vous ne verrez alors pas la sortie de débogage). Et encore plus simple, car il s'agit d'une simple délégation à une méthode existante que vous pourriez écrire: whoLetDogsOut.computeIfAbsent("snoop", String::isEmpty);
Cette délégation n'a pas besoin d' écrire de paramètres.
Pour être plus proche de l'exemple de votre question, vous pouvez l'écrire comme whoLetDogsOut.computeIfAbsent("snoop", key -> tryToLetOut(key));
(peu importe si vous nommez le paramètre k
ou key
). Ou écrivez-le comme whoLetDogsOut.computeIfAbsent("snoop", MyClass::tryToLetOut);
si tryToLetOut
est static
ou whoLetDogsOut.computeIfAbsent("snoop", this::tryToLetOut);
si tryToLetOut
est une méthode d'instance.