Parallele Programmierung auf dem Raspberry Pi

Seite 4: Tuning und Fazit

Inhaltsverzeichnis

Tatsächlich gäbe es noch Luft nach oben. Erstens verwendet das Programm die dynamische Typisierung von Python, was bequem für den Entwickler ist, aber Zeit kostet. Außerdem hat die mapper-Funktion die größte Last, deren Aufruf als Python-Methode mit dem kompletten Overhead der Skriptsprache erfolgt. Cython erlaubt die statische Typdeklaration als Erweiterung der Python-Syntax, und die Deklaration der Standarddatentypen kann wie in C erfolgen. Abbildung 8 zeigt das anhand eines Beispiels aus der Cython-Dokumentation.

Typdeklaration in Python und Cython (Abb. 7)

Anderseits sollten Entwickler übermütiges Umschreiben von Python- in Cython-Code vermeiden. Das kostet Entwicklungszeit und kann im Endeffekt weniger Verbesserung bringen als erwartet. Wie Donald Ervin Knuth ("Don" Knuth) sagte: "We should forget about small efficiencies, say about 97 % of the time: premature optimization is the root of all evil." Entwickler optimieren ein Programm nur dort, wo es wirklich zählt. Die kritischen Stellen finden sie mit Profiling-Tools. Dazu müssen sie den Hauptaufruf aus dem vorhergehenden Listing lediglich um ein paar Zeilen erweitern:

import pstats, cProfile
import pyximport; pyximport.install()
import oracle_lsnr_multiprocessing_mapreduce_test_07
cProfile.runctx("oracle_lsnr_multiprocessing_mapreduce_test.main()",
globals(), locals(), "Profile.prof")
s = pstats.Stats("Profile.prof")
s.strip_dirs().sort_stats("time").print_stats()

Profiling der mapper-Funktion (Abb. 8)

Das Ergebnis des Profiling der mapper-Funktion (s. Abb. 8) zeigt erwartungsgemäß, dass die meiste Zeit der Verarbeitung in der Regular-Expression-Methode search steckt. Das wäre ein heißer Kandidat zum Optimieren des Codes – beispielsweise durch das Ersetzen der Python-Methode durch C-Funktionen aus regex.h:

cdef extern from "regex.h" nogil:... 

Ein Diskussionsbeitrag zu dem Thema zeigt jedoch für einen konkreten Fall das umgekehrte Resultat: Die Einbindung führte zu einer verschlechterten Performance. Angeblich waren die C-Funktionen aus regex.h langsamer als die anderen aus Pythons re-Modul.

Eine andere interessante Alternative zum multiprocessing-Modul von Python wäre der Einsatz des cython.parallel-Moduls. Es hat verschiedene Methoden zur parallelen Verarbeitung der Daten und kann auch das GIL-Problem steuern. Außerdem unterstützt Cython die OpenMP-Funktionen. Das Einschalten dieser Features geschieht beim Kompilieren. Allerdings erfordern der Einsatz des Cython-Moduls und OpenMP zahlreiche Code-Anpassungen und mit großer Wahrscheinlichkeit eine wesentliche Änderung des Verarbeitungsalgorithmus. Positiv betrachtet gibt es genug zum Experimentieren in der parallelen Programmierung auf dem Raspberry Pi.

Mit einem Preis von etwa 35 Euro untermauert der kleine Einplatinencomputer Raspberry Pi die Hauptidee der gleichnamigen britischen Foundation. Er ist als gelungener, einfach aufgebauter und günstiger Heimcomputer bestens für IT-Experimente geeignet. Sein Vierkernprozessor auf ARM-Cortex-Basis ermöglicht den Einstieg in die Welt der parallelen Programmierung und fördert zudem die weitere Entwicklung auf Python.

Auch wenn der Raspberry freilich nicht mit High-Performance-Clustern für die parallele Berechnung mithalten kann, ist er definitiv keine lahme Ente. Ende Februar haben die Macher den jüngsten Raspberry Pi B 3 präsentiert, der mit einem 64-Bit-ARM-SoC bestückt ist und schneller als der Raspberry Pi 2 rechnet. Leider bietet das Modell keinen USB-3.0-Standard, der beim MapReduce-Verfahren eine zusätzliche Optimierung und Performance-Verbesserung auf Hardwareebene wäre.

Vladimir Poliakov
absolvierte 1995 Russian State Hydrometeorological University (RSHU) in St. Petersburg und arbeitete im Forschungsinstitut für Arktis und Antarktis. Nach seiner Auswanderung nach Deutschland war er seit 1998 in verschiedenen Softwarehäuser als Entwickler tätig und ist seit 2007 DBA und Solution Architect in Scientific Computing bei AREVA GmbH.


(rme)