Toujours quand j'utilise des expressions lambda comme ceci:
.map(obj -> foo.makeSomething(obj))
IntelliJ suggère: "Peut être remplacé par une référence de méthode ...". Et quand j'essaye alors:
.map(Foo::makeSomething)
J'obtiens la déclaration suivante: "Une méthode non statique ne peut pas être référencée à partir d'un contexte statique".
Pourquoi Idea me suggère-t-il d'utiliser une référence de méthode si elle n'est pas correcte?
Comme vous écrivez:
map(Foo::makeSomething)
le compilateur attend l'une de ces deux possibilités:
invoquer une méthode d'instance Foo.makeSomething()
sur le premier paramètre du lambda qui doit être défini comme un Foo
.
invoquer une méthode Foo.makeSomething()
statique.
La première possibilité est éliminée par le compilateur car le premier paramètre du lambda déclaré obj
n'est pas un Foo
.
Et selon votre message d'erreur, Foo.makeSomething()
est une méthode d'instance:
Méthode non statique ne peut pas être référencée depuis un contexte statique "
Ainsi, la seconde possibilité (invoquer une méthode Foo.makeSomething()
statique) n'est pas légale non plus, car makeSomething()
n'est pas statique.
En fait, vous voulez appliquer la méthode d'instance makeSomething()
à une variable qui ne fait pas partie des paramètres lambda.
Vous pouvez le faire, mais vous devez utiliser une autre syntaxe.
Au lieu de spécifier Foo::
, utilisez foo::
.
De cette manière, la méthode d’instance makeSomething()
sera appliquée à la variable foo
:
map(foo::makeSomething)
IntelliJ Intention
Notez que l'inspection qui indique des lambdas pouvant être remplacés par des références de méthodes peut également être automatiquement refactorisée par le IDE via une intention.
Pour cela, positionnez le curseur sur le lambda (n'importe où) et affichez les intentions contextuelles (Alt+Enter
par défaut). Vous devriez voir l'intention:
Remplacer lambda par la référence de la méthode
Quelques captures d'écran: