MINT lernen

Binäre Suche

Warum genügen in einer sortierten Liste mit einer Million Einträgen zwanzig Blicke?

1

Halbieren statt durchsehen

Ein Hotel speichert die Nummern seiner belegten Zimmer aufsteigend sortiert. Ist Zimmer 135 belegt? Ein Blick in die Mitte verrät, in welcher Hälfte man weitersuchen muss.

  • Voraussetzung:die Reihung ist sortiert — sonst sagt die Mitte nichts über die Hälften.
  • Suchbereich:die Indizes von links bis rechts; zu Beginn 0 bis Länge − 1.
  • Mitte:mitte = (links + rechts) / 2 mit ganzzahliger Division, z. B. \((0 + 10) / 2 = 5\), \((6 + 7) / 2 = 6\).
  • Treffer:a[mitte] = x — Index mitte zurückgeben.
  • Zu klein:a[mitte] < x — rechts weitersuchen: links ← mitte + 1.
  • Zu groß:a[mitte] > x — links weitersuchen: rechts ← mitte − 1.
  • Abbruch:gilt links > rechts, ist der Bereich leer — Rückgabe −1.
static int binaereSuche(int[] a, int x) {
    int links = 0;
    int rechts = a.length - 1;
    while (links <= rechts) {
        int mitte = (links + rechts) / 2;   // ganzzahlige Division
        if (a[mitte] == x) {
            return mitte;
        } else if (a[mitte] < x) {
            links = mitte + 1;              // x kann nur rechts liegen
        } else {
            rechts = mitte - 1;             // x kann nur links liegen
        }
    }
    return -1;                              // Bereich leer: links > rechts
}
2

Tracetabelle und Aufwand

Aufruf binaereSuche(zimmer, 135). Als ein Vergleich zählt jeder Blick auf a[mitte].

Vergleichlinksrechtsmittezimmer[mitte]Entscheidung
10105126126 < 135 → links ← 6
26108141141 > 135 → rechts ← 7
3676130130 < 135 → links ← 7
4777135gefunden → gib 7 zurück
  • Ergebnis:Index 7 nach 4 Vergleichen — die lineare Suche bräuchte 8.
  • Ohne Treffer:die Suche nach 110 endet mit links = 2 > rechts = 1 und liefert −1, ebenfalls nach 4 Vergleichen.
  • Halbieren:jeder Vergleich ohne Treffer schließt die Mitte und eine ganze Hälfte aus.

Du steuerst die Suche selbst: Vergleiche das markierte Element in der Mitte mit dem gesuchten Wert und entscheide, welche Hälfte bleibt — die andere wird weggelegt. Klicke dazu in die Hälfte oder nutze die Pfeiltasten. Achte auf die Grenzen links, rechts und mitte.

Suchbereich halbieren

Nr.linksrechtsmittea[mitte]Entscheidung

Halte fest: Jeder Vergleich halbiert den Suchbereich mindestens — bei 15 Elementen ist nach spätestens 4 Vergleichen Schluss, bei 16 nach spätestens 5.

Herleitung:
\(n\)
Start

Vor dem ersten Vergleich umfasst der Suchbereich alle \(n\) Elemente.

\(\dfrac{n}{2^k}\)
halbieren

Jeder Vergleich ohne Treffer lässt höchstens die Hälfte übrig — nach \(k\) Vergleichen also höchstens so viele Elemente.

\(\dfrac{n}{2^k} \ge 1\)
Bedingung

Ein weiterer Vergleich findet nur statt, solange noch mindestens ein Element im Bereich liegt.

\(2^k \le n\)
\(\cdot\, 2^k\)

Beide Seiten mit \(2^k\) multiplizieren.

\(k \le \log_2 n\)
\(\log_2\)

Da \(k\) ganzzahlig ist, gilt höchstens \(k = \lfloor\log_2 n\rfloor\) — so oft kann man ohne Treffer halbieren.

\(\text{Vergleiche} \le \lfloor\log_2 n\rfloor + 1\)
\(+\,1\)

Dazu kommt der letzte Vergleich im Bereich mit einem Element. Beispiel: \(n = 11\) ergibt \(\lfloor 3{,}46\rfloor + 1 = 4\).

Merke

Binäre Suche in einer sortierten Reihung: höchstens \(\lfloor\log_2 n\rfloor + 1\) Vergleiche · Abbruch ohne Treffer bei links > rechts

3

Allgemeine Hinweise

Immer mitte ± 1

Mit links = mitte; statt mitte + 1 bleibt der Bereich bei zwei Elementen gleich groß — die Schleife läuft endlos. Die Mitte ist nach dem Vergleich erledigt und gehört nicht mehr dazu.

Unsortiert? Erst sortieren

Auf einer unsortierten Reihung liefert die binäre Suche falsche Ergebnisse, ohne abzustürzen. Prüfe vorher, ob die Daten sortiert sind — sonst lineare Suche oder erst sortieren.

Doppelte Werte

Kommt x mehrfach vor, liefert die binäre Suche irgendeines der Vorkommen — nicht unbedingt das erste. Wer das erste braucht, muss nach einem Treffer links weitersuchen.

Videos