Berechnungen mit Bildern#

Wir haben im letzten Kapitel gesehen, dass Bilder in Form von Numpy-Arrays existieren. Hier werden wir verschiedene Arten von Bildverarbeitungsberechnungen betrachten, die wir mit solchen Arrays durchführen können, wie arithmetische Operationen, Kombinieren von Bildern usw.

Wir haben im letzten Kapitel gesehen, dass wir Bilder mit z.B. der Funktion np.random.random erstellen konnten. Lasst uns zwei kleine Bilder erstellen:

import numpy as np
from matplotlib import pyplot as plt
image1 = np.ones((3,5))
image1
array([[1., 1., 1., 1., 1.],
       [1., 1., 1., 1., 1.],
       [1., 1., 1., 1., 1.]])
image2 = np.random.random((3,5))
image2
array([[0.1389824 , 0.99979463, 0.82577042, 0.79474507, 0.23101268],
       [0.27034647, 0.01410389, 0.20435784, 0.0721552 , 0.61984191],
       [0.85459468, 0.58800162, 0.62462822, 0.01819988, 0.06607906]])

Einfache Berechnungen#

Zur Wiederholung aus dem letzten Kapitel haben wir gesehen, dass wir mit Bildern genauso rechnen können wie mit einfachen Zahlen:

image1_plus = image1 + 3
image1_plus
array([[4., 4., 4., 4., 4.],
       [4., 4., 4., 4., 4.],
       [4., 4., 4., 4., 4.]])

Dies gilt für alle grundlegenden Operationen wie Addition, Multiplikation usw. Sogar das Potenzieren funktioniert:

image1_plus ** 2
array([[16., 16., 16., 16., 16.],
       [16., 16., 16., 16., 16.],
       [16., 16., 16., 16., 16.]])

Bilder kombinieren#

Wenn Bilder die gleiche Größe haben, können wir sie hier wieder wie einfache Zahlen behandeln und Mathematik mit ihnen betreiben: wieder Addition, Multiplikation usw. Zum Beispiel:

image1 + image2
array([[1.1389824 , 1.99979463, 1.82577042, 1.79474507, 1.23101268],
       [1.27034647, 1.01410389, 1.20435784, 1.0721552 , 1.61984191],
       [1.85459468, 1.58800162, 1.62462822, 1.01819988, 1.06607906]])

Funktionen Pixel für Pixel#

Zusätzlich zur Erstellung verschiedener Arten von Arrays bietet Numpy auch Funktionen, die auf Arrays operieren können. In vielen Fällen ist die Eingabe ein Bild und die Ausgabe ist ein Bild derselben Größe, bei dem eine bestimmte Funktion auf jeden einzelnen Pixel angewendet wurde.

Zum Beispiel möchten wir vielleicht eine Logarithmusfunktion auf ein Bild anwenden, um den Wertebereich der Pixel zu reduzieren. Hier würden wir die Funktion np.log verwenden:

np.log(image2)
array([[-1.97340794e+00, -2.05388747e-04, -1.91438488e-01,
        -2.29733884e-01, -1.46528267e+00],
       [-1.30805091e+00, -4.26130469e+00, -1.58788269e+00,
        -2.62893591e+00, -4.78290819e-01],
       [-1.57127986e-01, -5.31025584e-01, -4.70598659e-01,
        -4.00634024e+00, -2.71690330e+00]])

Wie wir sehen können, hatte das Eingabebild 3 Zeilen und 5 Spalten und das Ausgabebild hat die gleichen Dimensionen. Sie finden in Numpy viele Funktionen, die auf diese Weise arbeiten, z.B. um eine Exponentialfunktion zu berechnen (np.exp()), für Trigonometrie (np.cos(), np.sin()) usw.

Bildstatistiken#

Eine andere Art von Funktionen nimmt ein Bild als Eingabe, gibt aber eine Ausgabe anderer Größe zurück, indem sie eine Statistik über das Bild oder Teile davon berechnet. Zum Beispiel können wir den Durchschnitt aller Pixelwerte von image2 berechnen:

np.mean(image2)
0.4215075982440046

Oder wir können angeben, dass wir den Mittelwert entlang einer bestimmten Dimension des Bildes berechnen wollen, in 2D entlang von Spalten oder Zeilen. Erinnern wir uns daran, was image2 ist:

image2
array([[0.1389824 , 0.99979463, 0.82577042, 0.79474507, 0.23101268],
       [0.27034647, 0.01410389, 0.20435784, 0.0721552 , 0.61984191],
       [0.85459468, 0.58800162, 0.62462822, 0.01819988, 0.06607906]])

Jetzt nehmen wir den Durchschnitt über die Spalten, was entlang der ersten Achse oder axis=0 bedeutet:

np.mean(image2, axis=0)
array([0.42130785, 0.53396671, 0.55158549, 0.29503338, 0.30564455])

Die gleiche Logik gilt für alle anderen statistischen Funktionen wie das Minimum (np.min()), das Maximum (np.max()), die Standardabweichung (np.std()), den Median (np.median()) usw.

Beachten Sie, dass die meisten dieser Funktionen auch direkt auf der Numpy-Array-Variable aufgerufen werden können. Zum Beispiel

np.std(image2)
0.3362691013424119

und

image2.std()
0.3362691013424119

sind völlig äquivalent. Im letzteren Fall, bei Verwendung der Punktnotation, könnte man sagen, dass std() eine Methode von image2 ist.

Schließlich möchten wir vielleicht einen Blick auf die tatsächliche Verteilung der Pixelwerte werfen. Dafür betrachten wir das Histogramm des Bildes.

number_of_bins = 10
min_max = [0,1]
histogram,bins = np.histogram(image2.ravel(),number_of_bins,min_max)
plt.hist(image2.ravel(), number_of_bins, min_max)
plt.show()
../_images/f1096d40d837e3fb2566f9bf2ec79e1169ddc427af6ff8d26e10e49374e021af.png

Übung#

Finden Sie im Modul numpy.random eine Funktion, die Poisson-Rauschen erzeugt, und erstellen Sie ein 4x9 Bild. Berechnen Sie dessen Mittelwert und Standardabweichung.