2013-04-25 41 views
9

Ich möchte erfahrenere Entwickler über eine einfache, aber für mich nicht offensichtliche Sache fragen. Angenommen, Sie einen solchen Code bekommen haben (Java):Zustand in Schleife überprüfen

for(int i=0; i<vector.size(); i++){ 
    //make some stuff here 
} 

stieß ich auf solche Aussagen sehr oft, vielleicht gibt es nichts falsch daran ist. Aber für mich scheint es unnötig, in jeder Iteration eine Größenmethode aufzurufen. Ich würde ein solcher Ansatz verwenden:

int vectorSize = vector.size(); 
for(int i=0; i<vectorSize; i++){ 
    //make some stuff here 
} 

Das gleiche hier:

for(int i=0; i<myTreeNode.getChildren().size(); i++){ 
    //make some stuff here 
} 

Ich bin definitiv kein Experte in der Programmierung noch, so ist meine Frage: Bin ich eine Lücke suchen, wo die Hecke Ganze oder ist es wichtig, sich um solche Details in professionellem Code zu kümmern?

+0

Danke - Ich hatte einige Probleme mit der Suche nach der Antwort für diese Frage ... –

+1

Manchmal ändern Sie die Größe des Vector innerhalb der Schleife. Es ist nichts falsch daran, die Größe vorher zu bekommen, vor allem, wenn die Größe Anruf ist teuer.Die Vektorgröße ist jedoch kein teurer Anruf. Verstehen Sie einfach, warum Sie die Größe vor dem Start der Schleife erhalten und verstehen, warum Sie die Größe nach jeder Iteration der Schleife überprüfen möchten. –

Antwort

8

Ein Methodenaufruf erfordert, dass die JVM tatsächlich zusätzliche Dinge tut. Was Sie tun, erscheint auf den ersten Blick wie eine Optimierung.

Einige JVM-Implementierungen sind jedoch intelligent genug für Inline-Methodenaufrufe, und für diese ist der Unterschied nicht vorhanden. Die Android-Programmierrichtlinien empfehlen zum Beispiel immer, das zu tun, worauf Sie hingewiesen haben, aber das JVM-Implementierungshandbuch (falls Sie es in die Finger bekommen) wird Ihnen sagen, ob es den Code für Sie optimiert oder nicht.

2

Normalerweise size() ist eine kleine Konstante Zeit-Operation und so die Kosten für den Aufruf size ist trivial im Vergleich zu den Kosten der Ausführung der Schleife Körper, und der Just-in-Time-Compiler kann sich um diese Optimierung für Sie kümmern; Daher kann diese Optimierung nicht sehr vorteilhaft sein.

Das heißt, diese Optimierung beeinträchtigt die Lesbarkeit des Codes nicht, daher ist sie nicht zu vermeiden. oft sollten Code-Optimierungen, die nur die Geschwindigkeit um einen kleinen Faktor beeinflussen (im Gegensatz zu zB einer Optimierung, die eine O (n) -Operation in eine O (1) -Operation ändert) aus diesem Grund vermieden werden, zB können Sie unroll a loop:

int i; 
int vectorSizeDivisibleBy4 = vectorSize - vectorSize % 4; // returns lowest multiple of four in vectorSize 
for(i = 0; i < vectorSizeDivisibleBy4; i += 4) { 
    // loop body executed on [i] 
    // second copy of loop body executed on [i+1] 
    // third copy of loop body executed on [i+2] 
    // fourth copy of loop body executed on [i+3] 
} 
for(; i < vectorSize; i++) { // in case vectorSize wasn't a factor of four 
    // loop body 
} 

Indem Sie die Schleife viermal abwickeln, reduzieren Sie die Anzahl der Male, die i < vectorSize um den Faktor vier bewertet wird, was Ihren Code zu einem unlesbaren Chaos macht (es könnte auch den Anweisungscache zerstören, was zu einem Negativ führt) Leistungseinfluss). Tu das nicht. Aber, wie ich schon sagte, int vectorSize = vector.size() fällt nicht in diese Kategorie, so muss es sein.

+0

aber natürlich, wie der Junge vermutete, dauert eine konstante Zeit mehr als eine zeitlose Operation. Netter Beitrag obwohl;) Prost –

0

Am ersten Anblick die Alternative Sie vorschlagen Nähte eine Optimierung, aber in Bezug auf die Geschwindigkeit ist es identisch mit dem gemeinsamen Ansatz, weil:

die Komplexität Uhrzeit des Anrufs von size() Funktion in einem Java-Vektor hat eine Komplexität der Ordnung O (1), da jeder Vektor immer eine Variable gespeichert hat, die seine Größe enthält, so dass Sie nicht seine Größe in jeder Iteration berechnen müssen, Sie greifen einfach darauf zu.

Hinweis: Sie können sehen, dass die Funktion size() in: http://www.docjar.com/html/api/java/util/Vector.java.html nur eine geschützte Variable elementCount zurückgibt.