La JVM empêche-t-elle les optimisations d’appels de queue?

J’ai vu cette citation sur la question: Quel est un bon langage fonctionnel sur lequel construire un service Web?

Scala, en particulier, ne prend pas en charge l’élimination des appels de queue, sauf dans les fonctions auto-récursives, ce qui limite les types de composition que vous pouvez effectuer (il s’agit d’une limitation fondamentale de la JVM).

Est-ce vrai? Si tel est le cas, en quoi consiste la JVM qui crée cette limitation fondamentale?

Ce post: Récursion ou Itération? pourrait aider.

En résumé, l’optimisation des appels de queue est difficile à réaliser dans la machine virtuelle Java à cause du modèle de sécurité et de la nécessité de toujours disposer d’une trace de stack. Ces exigences pourraient en théorie être sockets en charge, mais cela nécessiterait probablement un nouveau bytecode (voir la proposition informelle de John Rose ).

Il y a aussi plus de discussion dans le bogue Sun n ° 4726340 , où l’évaluation (à partir de 2002) se termine:

Je crois que cela pourrait être fait néanmoins, mais ce n’est pas une mince tâche.

Actuellement, des travaux sont en cours dans le projet Da Vinci Machine . Le statut du sous-projet d’appel de queue est répertorié comme “proto 80%”; il est peu probable que cela se passe en Java 7, mais je pense que cela a de très bonnes chances pour Java 8.

La limitation fondamentale est simplement que la JVM ne fournit pas d’appels de queue dans son code d’octet et, par conséquent, il n’existe aucun moyen direct pour un langage basé sur la machine virtuelle de fournir des appels de queue lui-même. Il existe des solutions de contournement qui peuvent produire un effet similaire (par exemple, le trampoline), mais elles entraînent des coûts énormes et rendent le code intermédiaire généré totalement inutile, ce qui rend un débogueur inutile.

Ainsi, la JVM ne peut prendre en charge aucun langage de programmation fonctionnel de qualité production tant que Sun n’a pas implémenté les appels de queue dans la JVM elle-même. Ils en discutent depuis des années mais je doute qu’ils vont jamais implémenter des appels de queue: ce sera très difficile car ils ont optimisé prématurément leur VM avant de mettre en œuvre ces fonctionnalités de base.

Il y a donc un argument très fort selon lequel Scala n’est pas un véritable langage de programmation fonctionnel: ces langages ont considéré les appels de queue comme une caractéristique essentielle depuis le lancement de Scheme il y a plus de 30 ans.

Scala 2.7.x prend en charge l’optimisation de l’appel de queue pour l’auto-récursion (une fonction appelant elle-même) des méthodes finales et des fonctions locales.

Scala 2.8 peut également être compatible avec le trampoline, une technique permettant d’optimiser les fonctions récursives.

Vous trouverez de nombreuses informations sur l’état de la récursion Scala dans le blog de Rich Dougherty .

En plus du document lié à Lambda The Ultimate (extrait du lien publié ci-dessus), John Rose de Sun a encore quelque chose à dire sur l’optimisation des appels de queue.

http://blogs.oracle.com/jrose/entry/tail_calls_in_the_vm

J’ai entendu dire que cela pourrait être mis en œuvre sur la JVM un jour. La Da Vinci Machine est entre autres à l’aide du support des appels de queue.

http://openjdk.java.net/projects/mlvm/

Toutes les sources indiquent que la JVM ne peut pas être optimisée en cas de récursion de la queue, mais en lisant Java performance tuning (2003, O’reilly), l’auteur a déclaré qu’il pouvait atteindre de meilleures performances de récursion.

Vous pouvez trouver sa réclamation à la page 212 (recherchez «récursivité de la queue», cela devrait être le deuxième résultat). Ce qui donne?