java - 使用lambda表达式(匿名内部类)传参是否有性能问题?
阿神
阿神 2017-04-18 10:53:20
0
3
1102

编程有一条原则如下:

避免创建不必要的对象:最好能重用对象,而不要在每次需要的时候就创建一个相同功能的新对象。

请看如下代码:

List<String> names = Arrays.asList("peter", "anna", "mike", "xenia");

 // 1、匿名内部类
Collections.sort(names, new Comparator<String>() {
    @Override
    public int compare(String a, String b) {
        return b.compareTo(a);
    }
});

//2、lambda表达式
Collections.sort(names, (a, b) -> b.compareTo(a));

是不是每次排序都创建了一个新的Comparator对象,导致性能降低?那么还主张使用Lambda表达式吗

阿神
阿神

闭关修行中......

répondre à tous(3)
Peter_Zhu

Répondez d'abord à votre question :
Un nouvel objet Comparator est-il créé à chaque tri, ce qui entraîne une réduction des performances ? Alors, préconisez-vous toujours d’utiliser des expressions Lambda ?
Non, je préconise

  1. La raison fondamentale
    Lamdba signifie qu'il ne s'agit pas du tout de sucre syntaxique pour les classes internes anonymes. C'est-à-dire que l'implémentation sous-jacente de l'expression Lambda n'est pas du tout l'implémentation de classes internes anonymes. Ce sont en fait deux choses

  2. Comment le prouver ?
    Les classes internes anonymes généreront en fait un fichier de classe lors de la compilation, nommé avec des numéros ClassName$, donc si la couche inférieure de l'expression Lamdba est également implémentée par des classes internes anonymes, elle générera certainement des fichiers internes similaires
    Nous écrivons donc simplement votre exemple dans des classes sous différents packages, puis vérifions l'effet compilé
    Une classe interne anonyme implémente InnerTest


    Ceci est un fichier de classe, vous pouvez voir qu'il y en a deux

    expression lambda LamdbaTest

    Cependant, il n'y a qu'un seul fichier de classe


    Donc il n'y a qu'une seule vérité, haha, évidemment, ce n'est pas du tout la même chose

  3. Comment l'expression Lamdba est-elle implémentée ?
    Nous pouvons jeter un œil à leur bytecode, afin que les différences sous-jacentes soient pleinement démontrées
    InnerTest

    LamdbaTest

    Vous pouvez voir que les instructions utilisées par les deux sont différentes. Lors de l'analyse des expressions Lamdba, la nouvelle instruction Invocationdynamic de Java 7 est utilisée. Si vous connaissez cette instruction, vous pouvez la comprendre instantanément. familier, vous pouvez demander à Du Niang
    Mais vous pouvez le comprendre directement à partir du nom de cette commande : Appel dynamique
    Par conséquent, contrairement aux classes internes anonymes qui sont compilées dans un fichier de classe, Lamdba L'expression est compilée dans une méthode statique. Nous pouvons le revoir en regardant -p La méthode générée est nommée lambda$main

    .

所以结合之前两个反编译的结果可以看到,lamdba表达式运行整体思路大致如下  
    1. lamdba表达式被编译生成当前类的一个私有静态方法  
    2. 在原调用Lamdba方法的地方编译成了一个invokedynamic指令调用,同时呢也生成了一个对应的BootstrapMethod  
    3. 当lamdba表达式被JVM执行,也就是碰到2中说到的invokedynamic指令,该指令引导调用LambdaMetafactory.metafactory方法,该方法返回一个CallSite实例
    4. 而这个CallSite实例中的target对象,也就是直接引用到一个MethodHandle实例,而这个MethodHandle实例会调用到1中生成的静态方法,在上面的例子就是`lambda$mainrrreee`这个方法,完成整个lamdba表达式的使用  
  1. Encore une chose
    En fait, vous pouvez voir que les expressions lamba sont en effet bien meilleures que les classes internes anonymes dans un sens, qu'il s'agisse de performances, de lisibilité ou de tendance générale ~ Haha, je veux pour dire tendance générale, car l'expression lamdba peut être optimisée dans un espace plus large. Quoi qu'il en soit, j'ai l'habitude de l'utiliser en java, et j'aime bien

.
阿神
  1. Chaque tri ne crée pas de nouvel objet Comparator Généralement, une fois l'instance correspondant à l'expression Lambda générée en mémoire, la JVM sera réutilisée ci-dessous. Pour des instructions spécifiques, veuillez vous référer à ce lien : Évaluation d'exécution des expressions Lambda

  2. En partant du principe que cela peut améliorer la lisibilité du programme et l'efficacité du développement, il est recommandé d'utiliser l'Lambdaexpression

刘奇
  1. Vous pouvez déclarer statiquement un objet de classe anonyme dans une expression Lambda

  2. Les petits objets qui vont et viennent ne sont pas un gros problème pour la JVM

Derniers téléchargements
Plus>
effets Web
Code source du site Web
Matériel du site Web
Modèle frontal
À propos de nous Clause de non-responsabilité Sitemap
Site Web PHP chinois:Formation PHP en ligne sur le bien-être public,Aidez les apprenants PHP à grandir rapidement!