Wie zu Squeeze Nanosekunden aus einer Java-Schleife

Die besten Tricks sind die einfachsten Tricks. So lesen Sie weiter auf einen einfachen Trick eingeführt werden, die herum für Alter gewesen ist - ein Trick, der die Hälfte der Laufzeit von einem Java-Programmschleife schneiden kann.

Stellen Sie sich vor, durch eine lange Liste von Namen zu suchen. Listing 1 hat einige Code, um die Idee zu illustrieren.

Listing 1: Die Suche nach einem Namen

Import java.io.File-Import java.io.IOException-Import java.util.Scanner-public class Haupt {static Scanner diskFile-static int MAX_SIZE = 100 statischen String name [] = new String [MAX_SIZE] -public static void main (String [] args) throws IOException {diskFile = new Scanner (neue Datei ( "names.txt")) - int numberOfNames = fillTheArray () - searchFor ( "Burd", numberOfNames) -} static int fillTheArray () {int i = 0-while (diskFile.hasNext () ich lt; MAX_SIZE) {name [i ++] = diskFile.next () -} return i-} static void searchFor (String whatToSearchFor, int numberOfNames) {int i = 0-während ich lt; numberOfNames  !name [i] .equals (whatToSearchFor)) { i ++ -}wenn ich lt; numberOfNames) { System.out.println ( "an Position gefunden" + i) -} Else { System.out.println ( "Not found") -}}}

Der Code in Listing 1 hat eine Reihe von Namen. Die Anzahl der Einträge in dem Array ist numberOfNames. Die fett gedruckten Code am unteren Ende der Liste überprüft wiederholt für einen Eintrag die gleichen Zeichen enthalten, wie whatToSearchFor (In diesem Beispiel der Name "Burd").

Die Schleife prüft auch wiederholt, um sicherzustellen, dass ich ist weniger als numberOfNames. Ohne diese Prüfung kann Ihr Programm laufen kommen mit einem Einsturz Null-Zeiger-Ausnahme oder Sie versuchen auf einen Index außerhalb der Feldgrenzen zuzugreifen. Hier ist der Grund:

  • Stellen Sie sich vor, dass die names.txt Datei enthält drei Namen: "Lockig", "Larry", und "Moe". Dann name [0] ist "Lockig", name [1] ist "Larry", und name [2] ist "Moe". Da ist kein name [3] Wert. (Präziser sein, name [3] ist Null.)

    Der Wert von numberOfNames ist 3. Ohne die ich lt; numberOfNames überprüfen, prüft das Programm, !name [3] .equals (whatToSearchFor). Aber name [3] ist Null so dass der Lauf des Programms sprengt mit der Null-Zeiger-Ausnahme.

  • Stellen Sie sich vor, dass die names.txt Datei 100 Namen enthält, und dass MAX_SIZE Dann ist 100. in jedem Eintrag der Name Array enthält eine ehrliche-to-Güte-String. Die Einträge in der Name Array name [0], name [1], und so weiter, den ganzen Weg bis zu Name [99]. Da ist kein name [100] Eintrag.

    Ohne das ich lt; numberOfNames überprüfen, prüft das Programm, !name [100] .equals (whatToSearchFor). Aber name [100] nicht vorhanden ist, so laufen die Programm den Staub mit der beißt Sie versuchen auf einen Index außerhalb der Feldgrenzen zuzugreifen.

So oder so, man muss offenbar zwei Dinge überprüfen jedes Mal durch die Schleife: Sie müssen prüfen, ob ich lt; numberOfNames und dann prüfen, ob !name [i] .equals (whatToSearchFor).

Die große Frage ist, kann man es besser machen? Können Sie nur eine Bedingung an Stelle von zwei überprüfen? Und die Antwort (als ob Sie bereits nicht erraten) ist: "Ja, Sie können." Diese besondere Trick verringert nicht die Laufzeit des Programms durch Sprünge und Grenzen, aber es ist ein netter Trick trotzdem. Hier ist die Idee:

Noch nie in so viele Namen lesen, die Sie nicht mindestens eine leere Array-Eintrag haben. Dann, nach dem letzten ehrlich-zu-Güte Array-Eintrag, fügen Sie eine weitere entry- nämlich den Namen ein, nach dem Sie suchen möchten. Mit diesen zusätzlichen Namen am Ende des Feldes, müssen Sie nicht halten Überprüfung ich lt; numberOfNames. Nun ist die andere Bedingung, !name [100] .equals (whatToSearchFor),muss falsch werden Vor Sie laufen von Array-Einträge.

Listing 2 enthält einen Code, diese Idee zu illustrieren. (Die Unterschiede zwischen Listing 2 und Listing 1 werden fett markiert 2. in Listing)

Listing 2: Eine etwas bessere Suchroutine

Import java.io.File-Import java.io.IOException-Import java.util.Scanner-public class Haupt {static Scanner diskFile-static int MAX_SIZE = 100 statischen String name [] = new String [MAX_SIZE] -public static void main (String [] args) throws IOException {diskFile = new Scanner (neue Datei ( "names.txt")) - int numberOfNames = fillTheArray () - searchFor ( "Burd", numberOfNames) -} static int fillTheArray () {int i = 0-while (diskFile.hasNext () ich lt; MAX_SIZE - 1) {Name [i ++] = diskFile.next () -} return i-} static void searchFor (String whatToSearchFor, int numberOfNames) {name [numberOfNames] = whatToSearchFor-int i = 0-while (!name [i] .equals (whatToSearchFor)) {I ++ -} if (i lt; numberOfNames) {System.out.println ( "an Position gefunden" + i) -} else {System.out.println ( "Not found") -}}}

In Listing 2 wird der Wert MAX_SIZE - 1 stellt sicher, daß das Array mindestens ein leerer Eintrag hat. Die Aussage

name [numberOfNames] = whatToSearchFor-

legt sich den Namen, den Sie nach dem letzten ehrlich-zu-Güte Array-Eintrag zu suchen möchten. Und die Bedingung !name [i] .equals (whatToSearchFor) prüft Array-Einträge, bis er entweder einen Namen aus der findet names.txt Datei oder den Namen, den Sie künstlich nach dem letzten Eintrag platziert.

Also das ist der Trick. Durch das Hinzufügen einer zusätzlichen Eintrag am Ende der Liste, gehen Sie von der Überprüfung zwei Bedingungen wiederholt

während ich lt; numberOfNames ! Name [i] .equals (whatToSearchFor))

auf die Überprüfung wiederholt nur eine Bedingung:

während (! Name [i] .equals (whatToSearchFor))

Hier ist eine interessante Tatsache über die Trick in diesem Artikel beschrieben wird: Sie haben nicht ein Java-Programm benötigen, um diesen Trick zu verwenden. In der Tat, müssen Sie nicht einmal einen Computer! Der Trick gilt für alle Arten von Situationen, die Suche einbeziehen - von Computern getan Suchen, durch Roboter erledigt Suchen, und auch von den Menschen getan sucht.

Stellen Sie sich eine lange Reihe von Feldern mit und erzählen Sie Ihren Assistent eine Grapefruit in einem der ersten hundert Kisten zu finden. (Morgen, jemand anderes beginnen wird von der 101st Feld suchen weiter.) Können Sie haben Ihre Assistenten Boxen zählen, wie sie suchen, aber wer will den Überblick über Box zählt zu halten, wie sie zu suchen? Wenn Sie bereits wissen, wo die 101st Feld ist, setzen Sie einen Marker auf diesem Feld und erzählen Sie Ihren Assistent der Markierung zu suchen, nach oben. Noch besser wäre es, lege eine Fälschung, Kunststoff Grapefruit in der 101. Box und einfach sagen, Ihr Assistent eine Grapefruit zu finden.

Die gleiche Art von Argumentation arbeitet in weniger gekünstelt Situationen. Ein Rezept für Lasagne erfordert 50 Minuten in den Ofen. Sie könnten Erhitzen der Lasagne, um 5:53 Uhr beginnen und auf die Uhr oder so jede Minute aussehen. Als endlich haben Sie 50 Minuten zählte, nehmen Sie die Lasagne aus dem Ofen.

Aber Minuten zu zählen ist ärgerlich. Während Sie auf die Uhr blicken zurück, könnten Sie einen Teil Ihres Lieblings TV-Spot zu verpassen. Statt all diese Zählung zu tun, setzen Sie einen Marker am Ende des Prozesses durch die Küche-Timer-Einstellung innerhalb von 50 Minuten zu gehen.

Sehen Sie? Es ist nicht nur Java. Es ist der gesunde Menschenverstand.

Menü