4.2. Module, Pakete, Bibliotheken#
Bisher haben wir Funktionen aufgerufen, die wir entweder selbst definiert haben, oder die bereits vorinstalliert waren. Diese vorinstallierten Funktionen sind Teil der sogenannten Python Standard Library, einer Sammlung von grundlegenden Funktionen und Datentypen. Darüber hinaus gibt es eine Vielzahl an Funktionen und sogar zusätzliche Datentypen, die andere Python-Nutzer:innen definiert und veröffentlicht haben. Diese Sammlungen von Funktionen und Datentypen werden häufig “Bibliotheken” (libraries) genannt, manchmal werden in diesem Zusammenhang aber auch die Begriffe “Modul” und “Paket” verwendet. Zunächst klären wir deswegen, was damit gemeint ist.
4.2.1. Module, Pakete, Bibliotheken#
Die Python-Dokumentation werden Pakete (engl. packages) einfach als “a collection of modules” definiert. Um zu verstehen, was Pakete sind, müssen wir also zunächst verstehen, was Module sind. In der Python-Dokumentation sind Module wie folgt definiert:
“A module is a file containing Python definitions and statements.”
Quelle: Python 3.11.3 Documentation.
Mit Datei (file) ist einfach ein Python-Skript gemeint, das verschiedene Anweisungen (statements) und Definitionen, zum Beispiel Funktionsdefinitionen, enthält. Module können Python-Nutzer:innen also selbst erstellen. Wenn man viele Funktionen zu einem bestimmten Anwendungszweck selbst definiert hat, möchte man diese nicht im Skript stehen haben, sondern speichert sie in einem separaten Skript, das dann “importiert” werden kann. Diese Skripte können auch online gestellt werden, damit andere Nutzer:innen die Funktionen auch importieren und nutzen können. Dieses Prinzip, den eigenen Code in Module aufzuteilen, die je einen unterschiedlichen Zweck haben, nennt man auch Modularisierung.
Module und Pakete werden also dazu verwendet, um seinen eigenen Code zu organisieren, oder um auf bestimmte Funktionalitäten zuzugreifen, die in Python nicht vordefiniert sind und die andere Python-Nutzer:innen definiert und veröffentlicht haben. Pakete enthalten vor allem Funktionen, aber auch zusätzliche Datentypen. Um darauf zuzugreifen, müssen Python-Pakete zuerst installiert und danach importiert werden.
Besonders komplexe Pakete, die verschiedene Unterpakete enthalten, werden auch Bibliothek (engl. library) genannt. Oft wird der Begriff “Bibliothek” aber auch einfach als Oberbegriff für verschiedene Arten von wiederverwendbarem Code verwendet. Der Einfachheit halber sprechen wir im Folgenden meist einfach von Paketen, auch dann, wenn eigentlich Module oder Bibliotheken gemeint sind.
Die Funktionen, die wir bisher kennengelernt haben, waren alle in Python vordefiniert. Wir mussten deswegen keine Pakete installieren und laden, um sie zu nutzen.
4.2.2. Pakete installieren#
Es gibt verschiedene Wege, Python-Pakete zu installieren. Da wir unser JupyterLab in einer virtuellen Umgebung ausführen werden und hierzu einen eigenen Kernel erstellen (-> s. Installation und Setup), verwenden wir den folgenden Code, um Pakete zu installieren:
# Python-Paket aus dem Jupyter Notebook heraus installieren
# import sys
# !conda install --yes --prefix {sys.prefix} pandas
Die Kommentare müsst ihr vor dem Ausführen natürlich entfernen.
Mit !conda list
kann anschließend eine Liste aller in der aktuellen Umgebung installierten Bibliotheken ausgegeben werden.
4.2.3. Pakete importieren#
Installierte Pakete müssen immer am Anfang eines Jupyter Notebooks importiert werden, bevor sie verwendet werden können:
import sys
sys
ist ein Modul aus der Python Standard Library, deswegen muss es nicht installiert werden und kann direkt importiert werden. Welche Module und Pakete bereits vorinstalliert sind, könnt ihr hier nachlesen.
Es ist auch möglich, nur einzelne Funktionen oder einen kleine Menge der Funktionen aus einem Paket zu importieren. Das ist allgemein effizienter und besonders wenn ihr nur eine bestimmte Funktion aus einem Paket benötigt, solltet ihr nur diese Funktion oder das entsprechende Modul importieren, und nicht das Paket im Gesamten. Um das zu tun, werden die Schlüsselworte from ... import...
verwendet.
from bs4 import BeautifulSoup
Für manche Pakete wird beim Importieren der Konvention nach ein Alias verwendet, also eine Kurzform des Paketnamens:
import pandas as pd
Durch die import-Anweisung wird ein Namensraum (engl. namespace) mit dem Namen des Pakets erstellt. In der Anweisung import sys
hat der Namensraum des importierten Moduls den Namen sys
. In der Anweisung import pandas as pd
wird dagegen der Name des Namensraums der Bibliothek pandas
manuell festgelegt, nämlich als pd
.
Funktionen aus dem importierten Paket können aufgerufen werden, indem zuerst der Name des Namensraums adressiert wird, gefolgt von einem Punkt und dem Funktionsnamen, also zum Beispiel könnten wir die Funktion getsizeof()
aus dem Modul sys
verwenden, um uns die Größe eines Objekts im Speicher in Bytes ausgeben zu lassen:
wort = "Hallo"
sys.getsizeof(wort)
54
4.2.4. Welche Pakete gibt es denn alles?#
Wenn ihr nach einer bestimmten Funktionalität sucht, dann empfiehlt es sich, zunächst auf der Seite https://pypi.org/ nach einem Stichwort zu suchen. Diese Seite durchsucht verschiedene Online-Plattformen, auf denen Python Nutzer:innen ihre Pakete veröffentlicht haben.
Zu den meisten Paketen gibt es eigene Dokumentationsseiten, die von den Python Nutzer:innen gepflegt werden, die das Paket entwickelt haben. Um zu verstehen, welche Funktionalitäten ein bestimmtes Paket zur Verfügung stellt, solltet ihr euch die Dokumentationsseiten zu des Pakets durchlesen.
Dokumentationsseiten zur Bibliothek pandas: https://pandas.pydata.org/docs/index.html
4.2.5. Pakete: Mehr als nur Funktionen#
Eingangs habe ich erwähnt, dass Python-Pakete neben Funktionen auch nutzerdefinierte Datentypen enthalten können.
Zum Beispiel hat Wes McKinney, ein US-amerikanischer Data Scientist, bei seiner Arbeit mit ökonometrischen Daten bemerkt, dass er immer wieder bestimmte Abläufe benötigte, um seine Daten zu analysieren. Er hat auch bemerkt, dass die existierenden Python-Datentypen nicht besonders effizient waren, um seine Daten zu verarbeiten und zu speichern. Da McKinney vor allem mit Daten gearbeitet hat, die in Tabellenform vorlagen, wollte er auch in Python mit Objekten arbeiten, auf die dieselben Operationen angewendet werden können wie auf Exceltabellen. Er hat deswegen einen neuen Datentyp definiert: einen DataFrame. Das Python-Skript, in dem er seinen DataFrame-Datentyp definiert hat, hat er zusammen mit den Skripten, in denen er die Funktionen zur Datenanalyse definiert hat, als neue Bibliothek mit dem Namen pandas veröffentlicht. Damit andere Nutzer:innen auch verstehen, was die Funktionen machen und wie sein neuer Datentyp zu verwenden ist, hat er seine Bibliothek online dokumentiert. Hier ist z.B. die Dokumentationsseite zum pandas-DataFrame: https://pandas.pydata.org/docs/reference/api/pandas.DataFrame.html
Auf der Dokumentationsseite stoßt ihr auf drei Begriffe, die wir bisher nicht erwähnt haben: Datenstruktur (data structure), Klasse (class) und Attribute (attributes).
Datenstruktur ist ein Begriff, der oft nicht ganz klar definiert verwendet wird. Auf den Pandas-Dokumentationsseiten können wir nachlesen, wie McKinney diesen Begriff definiert:
“The best way to think about the pandas data structures is as flexible containers for lower dimensional data. For example, DataFrame is a container for Series, and Series is a container for scalars. We would like to be able to insert and remove objects from these containers in a dictionary-like fashion.”
Quelle: pandas 2.0.1 Documentation
Eine pandas-Datenstruktur ist also eigentlich einfach ein zusammengesetzter Datentyp.
Jetzt zum zweiten Begriff. Wenn Nutzer:innen eigene Datentypen definieren wollen, dann verwenden sie dazu Klassen. In der Python-Dokumentation werden Klassen wie folgt definiert:
“Classes provide a means of bundling data and functionality together. Creating a new class creates a new type of object, allowing new instances of that type to be made. Each class instance can have attributes attached to it for maintaining its state. Class instances can also have methods (defined by its class) for modifying its state.”
Quelle: Python 3.11.3 Documentation
Zur Definition von Klassen wird das Signalwort class
verwendet statt das Signalwort def
, das wir von der Definition von Funktionen kennen. Bei der Klassendefinition wird wie bei Funktionsdefinitionen auch ein Name der Klasse festgelegt. Diesen Namen verwenden wir, um den Typ eines Objekts zu benennen: Also im Beispiel unten ist df ein Objekt vom Typ DataFrame. Wir haben ja zu Anfang erwähnt, dass alles in Python ein Objekt ist, und dass jedes Objekt einen Typ hat, der bestimmt, welche Eigenschaften das Objekt hat und welche Operationen darauf angewendet werden können. In der Klassendefinition werden genau diese Eigenschaften und Operationen festgelegt. Wir haben schon mehrmals besprochen, dass die Operationen, die für Objekte eines Datentyps definiert sind, Methoden genannt werden. Die Eigenschaften, die für Objekte eines Datentyps definiert sind, heißen dagegen Attribute.
Note
In der Python-Dokumentation heißen diese Eigenschaften genau genommen “Data Attributes”, um sie von Methoden zu unterscheiden, die nämlich auch eine Art von Attributen sind, und zwar eigentlich “Prozedurale Attribute”. In der Alltagssprache wird aber oft einfach nur von Attributen und Methoden gesprochen.
Mithilfe des Klassennamens können dann neue Instanzen (Exemplare) der Klasse erstellt werden, also eben Objekte vom Typ X.
Beispiel: Erstellt ein Objekt vom Typ Dictionary, das irgendwelche Strings als Schlüssel und Listen als Werte enthält. Nennt das Dictionary daten. Erstellt dann ein Objekt vom Typ DataFrame, indem ihr den folgenden Code ausführt (ohne die Kommentarzeichen):
# df = pd.DataFrame(daten)
# print(df)
Jetzt können wir Methoden auf dieses Objekt anwenden, welche für pandas-DataFrames definiert sind. Zum Beispiel die Methode head, welche per Default die ersten fünf Zeilen des Dataframes ausgibt:
# Die ersten 5 Zeilen des DataFrames ausgeben lassen
# df.head()
# Erste 2 Zeilen ausgeben lassen
# df.head(2)
Es ist auch möglich, Attribute (Eigenschaften) des Objekts abzufragen. Dazu wird genau wie beim Zugriff auf Methoden der Punkt-Operator verwendet. Aber anders als beim Aufruf von Methoden werden aber beim Zugriff auf Attribute keine runden Klammern verwendet! Für Objekte vom Typ DataFrame ist zum Beispiel das Attribut columns
definiert, welches die Spaltennamen des DataFrames beschreibt:
# Auf Attribut columns des DataFrames df zugreifen
# df.columns
4.2.6. Quellen#
Python Package Index (PyPI). URL: https://pypi.org/.
Ana Bell. Object Oriented Programming. 2016. URL: https://ocw.mit.edu/courses/6-0001-introduction-to-computer-science-and-programming-in-python-fall-2016/resources/lecture-8-object-oriented-programming/.
Austin Cepalia. Scripts, Modules, Packages, and Libraries. URL: https://realpython.com/lessons/scripts-modules-packages-and-libraries/.
Johannes Ernesti and Peter Kaiser. Modularisierung. 2023. URL: https://openbook.rheinwerk-verlag.de/python/20_001.html.
Wes McKinney. pandas 2.0.1 Documentation: Data Structures. 2023. URL: https://pandas.pydata.org/docs/getting_started/overview.html#data-structures.
Wes McKinney. pandas 2.0.1 Documentation: Intro to Data Structures. 2023. URL: https://pandas.pydata.org/docs/user_guide/dsintro.html.
Wes McKinney. pandas 2.0.1 Documentation: pandas.DataFrame. 2023. URL: https://pandas.pydata.org/docs/reference/api/pandas.DataFrame.html.
Wes McKinney. pandas 2.0.1 Documentation. 2023. URL: https://pandas.pydata.org/docs/index.html.
Erik Westra. Modular Programming in Python. Ch. 1: Introducting Modular Programming. 2016. URL: https://www.packtpub.com/product/modular-programming-with-python/9781785884481.
Python 3.11.3 Documentation. Classes. URL: https://docs.python.org/3/tutorial/classes.html.
Python 3.11.3 Documentation. Modules: Packages. URL: https://docs.python.org/3/tutorial/modules.html#packages.
Python 3.11.3 Documentation. sys – System-Specific Parameters and Functions. URL: https://docs.python.org/3/library/sys.html#sys.getsizeof.