web-dev-qa-db-fra.com

Java pour la boucle par rapport à la boucle while. Différence de performance?

Supposons que j'ai le code suivant, il y en a trois pour faire une boucle. Est-ce que ça fonctionnerait vite si je changeais la boucle la plus externe pour boucle while? merci ~~ 

int length = 200;
int test = 0;
int[] input = new int[10];

for(int i = 1; i <= length; i++) {
    for (int j = 0; j <=length - i; j++) {
        for (int k = 0; k < length - 1; k++) {
            test = test + input[j + k];
        }
    }
}
25
KKLong

Non, changer le type de boucle n'aurait pas d'importance.

La seule chose qui puisse accélérer les choses serait d'avoir moins d'imbrication de boucles et de boucles sur moins de valeurs.

La seule différence entre une boucle for et une boucle while est la syntaxe permettant de les définir. Il n'y a pas de différence de performance du tout.

int i = 0;
while (i < 20){
    // do stuff
    i++;
}

Est le même que:

for (int i = 0; i < 20; i++){
    // do Stuff
}

(En réalité, la boucle for est un peu meilleure, car i sera hors de portée après la boucle alors que i restera dans le cas de la boucle while.)

Une boucle for est simplement une manière plus jolie de boucler sa syntaxe.

52
jjnguy

Ce type de micro-optimisation est inutile.

  • Une boucle while ne sera pas plus rapide.
  • La structure de la boucle est pas votre goulot d’étranglement.
  • Optimisez d'abord votre algorithme.
  • Mieux encore, n’optimisez pas d’abord. Optimisez uniquement lorsque vous avez découvert que votre algorithme présente un goulet d'étranglement qui n'est pas dépendant des E/S.
28
Bombe

vous ne pouvez pas l'optimiser en le changeant en tant que.

vous pouvez simplement augmenter la vitesse très très très très peu en changeant la ligne

for (int k = 0; k < length - 1; k++) {

par

for (int k = 0; k < lengthMinusOne; k++) {

où lengthMinusOne est calculé avant

cette soustraction ne fait que calculer presque (200x201/2) x (200-1) fois et le nombre est très petit pour l'ordinateur :)

9
ufukgun

Quelqu'un a suggéré de tester les boucles while contre for. J'ai donc créé du code pour vérifier si les boucles while ou for étaient plus rapides. en moyenne, plus de 100 000 tests, la boucle while était plus rapide environ 95% du temps. Je l'ai peut-être mal codé, je suis assez novice dans le codage, même si je n'ai couru que 10 000 boucles, leur durée de vie a été relativement homogène. 

edit Je n’ai pas déplacé toutes les valeurs du tableau lorsque j’ai essayé de tester davantage. Corrigé afin qu'il soit plus facile de changer le nombre d'essais que vous exécutez.

import Java.util.Arrays;

class WhilevsForLoops {

 public static void main(String[] args) {

final int trials = 100; //change number of trials
final int trialsrun = trials - 1;

boolean[] fscount = new boolean[trials]; //faster / slower boolean
int p = 0; // while counter variable for for/while timers



while (p <= trialsrun) {
     long[] forloop = new long[trials];
     long[] whileloop = new long[trials];

     long systimeaverage; 
     long systimenow = System.nanoTime();
     long systimethen = System.nanoTime();

     System.out.println("For loop time array : ");
     for (int counter=0;counter <= trialsrun; counter++) {
         systimenow = System.nanoTime();
         System.out.print(" #" + counter + " @");
         systimethen = System.nanoTime();
         systimeaverage = (systimethen - systimenow);
         System.out.print( systimeaverage + "ns |");

         forloop[counter] = systimeaverage; 
     }

     int count = 0;
     System.out.println(" ");
     System.out.println("While loop time array: ");
     while (count <= trialsrun) {
         systimenow = System.nanoTime();
         System.out.print(" #" + count + " @");
         systimethen = System.nanoTime();
         systimeaverage = (systimethen - systimenow);
         System.out.print( systimeaverage + "ns |");

         whileloop[count] = systimeaverage;
         count++;
     }


     System.out.println("===============================================");
     int sum = 0;

     for (int i = 0; i <= trialsrun; i++) {
        sum += forloop[i];
     }

     System.out.println("for loop time average: " + (sum / trials) + "ns");

     int sum1 = 0;

     for (int i = 0; i <= trialsrun; i++) {
         sum1 += whileloop[i];
     }
     System.out.println("while loop time average: " + (sum1 / trials) + "ns");



     int longer = 0;
     int shorter = 0;
     int gap = 0;

     sum = sum / trials;
     sum1 = sum1 / trials; 

     if (sum1 > sum) {
        longer = sum1;
        shorter = sum;
     }
     else {
        longer = sum;
        shorter = sum1;
     }

     String longa;

     if (sum1 > sum) {
        longa = "~while loop~";
     }
     else {
         longa = "~for loop~";
     }

     gap = longer - shorter; 
     System.out.println("The " + longa + " is the slower loop by: " + gap + "ns");
     if (sum1 > sum) {
     fscount[p] = true; }
     else {
         fscount[p] = false;
     }
     p++;
}

    int forloopfc=0;
    int whileloopfc=0;

    System.out.println(Arrays.toString(fscount));

    for(int k=0; k <= trialsrun; k++) {
        if (fscount[k] == true) {
            forloopfc++; }
            else {
                whileloopfc++;}

    }

    System.out.println("--------------------------------------------------");

    System.out.println("The FOR loop was faster: " + forloopfc + " times.");
    System.out.println("The WHILE loop was faster: " + whileloopfc + " times.");
 }

}
6
Sleepy

Même si l'hypothèse selon laquelle la boucle while était plus rapide que la boucle for était vraie (et ce n'est pas le cas), les boucles que vous deviez modifier/optimiser ne seraient pas les boucles externes mais les boucles internes, car elles sont exécutées plusieurs fois. .

2
fortran

La différence entre for et while est sémantique :

  • Dans une boucle while, vous bouclez tant que la condition est vraie, ce qui peut varier beaucoup, car vous pourriez, dans votre boucle, modifier des variables en utilisant pour évaluer la condition while.
  • Habituellement, dans une boucle for, vous bouclez N heure. Ce N peut être variable, mais ne se déplace pas avant la fin de votre boucle N, car les développeurs ne modifient généralement pas les variables évaluées dans la condition de boucle. 

C'est un moyen d'aider les autres à comprendre votre code. Vous n'êtes pas obligé de ne pas modifier les variables de boucle, mais c'est une pratique courante (et bonne).

2
Clement Herreman

voici un utile link à un article sur le sujet

selon elle, les While et For sont presque deux fois plus rapides, mais les deux sont identiques.

MAIS cet article a été écrit en 2009 et je l’ai donc essayé sur ma machine et voici les résultats:

  • utilisant Java 1.7: l'Iterator était environ 20% -30% plus rapide que pour et tant que (qui étaient toujours les mêmes)
  • en utilisant Java 1.6: l'Iterator était environ 5% plus rapide que pour et pendant (qui étaient toujours les mêmes)

donc je suppose que la meilleure chose à faire est de le chronométrer sur votre propre version et machine et de conclure de cela

2
levtatarov

Non, vous continuez à boucler exactement le même nombre de fois. Cela n'aurait aucune importance. 

1
aquinas

Regardez votre algorithme! Savez-vous à l'avance quelles valeurs de votre tableau sont ajoutées plusieurs fois?

Si vous savez que vous pourriez réduire le nombre de boucles et que cela améliorerait les performances.

1
Roalt

Est-ce que quelqu'un a essayé comme ça ...

int i = 20;
while (--i > -1){
    // do stuff
}

Par rapport à:

for (int i = 0; i < 20; i++){
    // do Stuff
}
0
Danilo Castro
0
Abhishek Gaikwad

Sur cette base: https://jsperf.com/loops-analyze (pas créé par moi), la boucle while est 22% moins rapide qu'une boucle for en général Au moins en Javascript c'est.

0
Arash R

Il n'y aurait pas de différence de performance. Essaye le!

La JVM et le compilateur transforment les deux boucles en quelque chose comme:

    label:
       ;code inside your for loop.
    LOOP label
0
Adrian

Cela n'aurait d'importance que si vous utilisez une programmation multi-thread ou multi-processeurs. Ensuite, cela dépend aussi de la façon dont vous affectez les boucles aux différents processeurs/threads.

0
Extrakun