Wir schreiben eine Funktion namens binary_search(li, el). Die Funktion nimmt eine sortierte Liste li und ein gesuchtes Element el an. Wenn sie das Element in der Liste findet, gibt sie die Position (den Index) des Elements zurück. Wenn nicht, gibt sie None zurück.

Vor uns liegt eine sortierte Liste mit dem kleinsten Element ganz links und dem grössten Element ganz rechts. Bei der Binärsuche schauen wir uns jeweils das mittlere Element des Suchbereichs1) an und vergleichen es mit dem gesuchten Element. Es ergeben sich drei Möglichkeiten:

  1. Das mittlere Element entspricht dem gesuchten Element. Also geben wir den Index des mittleren Elements zurück und sind fertig.
  2. Das mittlere Element ist grösser als das gesuchte Element. Also schränken wir den Suchbereich ein, sodass alles ab der Mitte rechts nicht weiter betrachtet wird.
  3. Das mittlere Element ist kleiner als das gesuchte Element. Also müssen wir nur noch in dem Bereich suchen, der rechts der Mitte liegt.

Bei 2. und 3. wird der Suchbereich halbiert und es ergibt sich daraus eine neue Mitteposition. Das Element an dieser Position verleichen wir erneut mit dem gesuchten Element. Wir wiederholen diese Schritte solange, bis:

  • das Element gefunden wurde oder
  • der Suchbereich nicht mehr kleiner werden kann. In diesem Fall haben wir das Element nicht gefunden. Also geben wir None zurück.

Wir programmieren also einen Algorithnus, bei dem eindeutige Schrite immer wieder durchgeführt werden – solange, bis die Arbeit erledigt ist. Wie bei den meisten Algorithmen sind hierzu zuerst ein paar einmalige Schritte nötig. Dann kommt eine Schleife, in der die Schritte stehen, die wiederholt werden sollen.

Nachdem wir den Funktionskopf hingeschrieben haben, legen wir die beiden Variablen left und right fest, mit denen wir den Suchbereich abstecken. Zu Beginn ist left 0 und right so gross wie der grösste Index der Liste.

Python

Wir müssen so lange suchen, wie wir den Suchbereich noch verkleinern können. Es kann sein, dass solange gesucht wird, bis der Suchbereich sich nur noch auf ein einziges Element berschränkt. Dann sind die Variablen left und right gleich gross. Wenn hier nichts gefunden wird, müssen wir abbrechen. Wir suchen also solange, wie left kleiner als oder gleich gross wie right ist.2)

Python

Zuerst berechnen wir die Mitteposition. Sie ergibt sich aus zwei Schritten: Erstens von der rechten Position die linke abziehen und diesen Wert durch zwei teilen. Zweitens müssen wir hierzu den linke Position hinzuaddieren. Also: middle = left + (right - left) // 2. Dieser Term lässt sich in eine einfachere Form bringen: middle = (left + right) // 2.3)

Danach vergleichen wir das Element an der Mitteposition mit dem gesuchten Element. Da es drei Möglichkeiten gibt, ist eine if-elif-else-Verzweigung geeignet:

  • Wenn das Element an der Mitteposition gleich gross ist wie das gesuchte Element, geben wir die Mitteposition zurück.
  • Wenn das Element an der Mitteposition grösser ist als das gesuchte Element, befindet sich das gesuchte Element links davon. Wir begrenzen den Suchbreich auf die linke Hälfte, indem wir die Variable rechts auf die Mitteposition - 1 setzen.
  • Wenn das Element an der Mitteposition kleiner ist als das gesuchte Element, befindet sich das gesuchte Element links davon. Wir begrenzen den Suchbreich auf die rechte Hälfte, indem wir die Variable links auf die Mitteposition + 1 setzen.

++ Python

   middle = (left + right) // 2
   if li[middle] == el:
      return middle
   elif li[middle] < el:
      left = middle + 1
   else:
      right = middle - 1

+

In dieser sortierten Liste mit 16 Zahlen wird nach der Zahl 42 gesucht. Der Suchbereich wird duch die Variablen l und r (für links und rechts) begrenzt. Zu Beginn erstreckt sich der Suchbereich über die gesamte Liste: l ist 0 und r ist so gross wie der höchste Index der Liste: len(li)-1.


1)
Der Suchbereich ist zu Beginn so breit wie die gesamte Liste, wird aber schnell sehr viel kleiner.
2)
Diese Bedingung ist nicht mehr erfüllt, wenn der Vergleich beispielsweise ergibt, dass das gesuchte Element kleiner ist als dasjenige, das hier als einziges übrig bleibt: Denn dann wird die Variable right so verändert, dass sie kleiner wird als left.
3)
Wir verwenden // statt /, damit unsere Division immer ganze Zahlen und keine Kommazahlen ergibt.
  • gf_informatik/suchen_und_sortieren/binaersuche/anleitung.1686075456.txt.gz
  • Zuletzt geändert: 2023-06-06 18:17
  • von gra