Answer to Question 1-1
Aktivierungsfunktionen in tiefen neuronalen Netzen müssen aus folgenden Gründen nichtlinear sein:

1. Ausdrucksstärke: Nichtlineare Aktivierungsfunktionen ermöglichen es dem Netzwerk, komplexe nichtlineare Zusammenhänge in den Daten zu lernen und zu modellieren. Lineare Aktivierungsfunktionen würden das Netzwerk auf das Lernen linearer Beziehungen beschränken, unabhängig von der Anzahl der Schichten. Mit nichtlinearen Funktionen können auch hochkomplexe Muster und Zusammenhänge gelernt werden.

2. Hierarchische Repräsentationen: Durch die Verwendung nichtlinearer Aktivierungen in mehreren Schichten können neuronale Netze hierarchische Repräsentationen der Eingabedaten lernen. Jede Schicht kann zunehmend abstraktere und komplexere Merkmale aus den Ausgaben der vorherigen Schicht extrahieren. Diese Hierarchie ermöglicht es dem Netzwerk, die zugrunde liegende Struktur der Daten auf mehreren Abstraktionsebenen zu erfassen.

3. Backpropagation: Nichtlineare Aktivierungsfunktionen sind für das Training tiefer Netze mit Backpropagation unerlässlich. Der Gradient, der während der Backpropagation berechnet wird, hängt von den Ableitungen der Aktivierungsfunktionen ab. Lineare Aktivierungen würden zu einem konstanten Gradienten führen, was das Lernen in tieferen Schichten erschwert. Nichtlineare Funktionen wie ReLU, Sigmoid oder Tanh haben bedeutungsvolle Gradienten, die das effektive Lernen in tiefen Architekturen ermöglichen.

4. Universelle Approximation: Es wurde gezeigt, dass neuronale Netze mit mindestens einer versteckten Schicht und nichtlinearen Aktivierungen universelle Funktionsapproximatoren sind. Das bedeutet, sie können jede stetige Funktion mit beliebiger Genauigkeit annähern, vorausgesetzt, das Netz ist groß genug. Diese Eigenschaft gilt nicht für rein lineare Netze.

Zusammenfassend sind nichtlineare Aktivierungsfunktionen entscheidend für die Fähigkeit tiefer neuronaler Netze, komplexe Muster zu lernen, hierarchische Repräsentationen zu bilden und als leistungsfähige universelle Approximatoren zu fungieren. Sie ermöglichen den Netzen, über einfache lineare Transformationen hinauszugehen und die zugrunde liegenden nichtlinearen Beziehungen in den Daten zu erfassen.





****************************************************************************************
****************************************************************************************




Answer to Question 1-2
LayerNorm, BatchNorm und InstanceNorm sind verschiedene Normalisierungstechniken, die beim Training von neuronalen Netzen eingesetzt werden, um das Training zu stabilisieren und zu beschleunigen. Hier die Unterschiede:

LayerNorm (Layer Normalization): 
- Normalisiert die Aktivierungen über alle Neuronen innerhalb eines Layers, d.h. es werden Mittelwert und Varianz pro Layer berechnet und die Aktivierungen damit normalisiert.
- Unabhängig von der Batch-Größe, da die Statistiken nur über die Neuronen eines Layers berechnet werden.
- Wird häufig bei Modellen mit variablen Sequenzlängen wie Transformer eingesetzt.

BatchNorm (Batch Normalization):
- Normalisiert die Aktivierungen über eine Mini-Batch, d.h. es werden Mittelwert und Varianz pro Feature-Map über die Beispiele im Batch berechnet. 
- Führt eine zusätzliche Skalierung und Verschiebung der normalisierten Werte mit erlernbaren Parametern durch.
- Erfordert eine ausreichend große und repräsentative Batch-Größe für aussagekräftige Statistiken.
- Wird sehr häufig in CNNs eingesetzt.

InstanceNorm (Instance Normalization):
- Normalisiert die Aktivierungen pro Beispiel und Feature-Map, d.h. es werden Mittelwert und Varianz für jedes einzelne Beispiel separat berechnet.
- Unabhängig von der Batch-Größe, da Statistiken pro Beispiel berechnet werden.
- Häufig verwendet in GANs und Stil-Transfer-Anwendungen.

Diese Normalisierungstechniken helfen aus folgenden Gründen, das Training zu stabilisieren:

1. Sie sorgen dafür, dass die Aktivierungen in einem begrenzen Wertebereich bleiben und nicht "explodieren". Dadurch werden extreme Gradienten vermieden.

2. Sie reduzieren die Änderung der Verteilung der Aktivierungen zwischen den Schichten (Internal Covariate Shift), was das Training beschleunigt.

3. Durch die Normalisierung können höhere Lernraten verwendet werden, was ebenfalls zu einer Beschleunigung des Trainings führt.

4. Die Normalisierung fungiert als eine Art Regularisierung und kann Overfitting reduzieren, da die Beispiele im Batch (bei BatchNorm) einen regularisierenden Effekt aufeinander haben.

Insgesamt tragen diese Normalisierungstechniken dazu bei, das Training von tiefen neuronalen Netzen stabiler und effizienter zu machen, was die Entwicklung immer komplexerer Modelle ermöglicht hat.





****************************************************************************************
****************************************************************************************




Answer to Question 1-3
Für die Berechnung der Ausgabe des rekurrenten Netzes im letzten Zeitschritt gehe ich folgendermaßen vor:

1. Die Eingabewerte seien mit x_t bezeichnet, wobei t der Zeitschritt ist. Da die Eingabewerte ganzzahlig und skalar sind, ist x_t eine einzelne Zahl für jeden Zeitschritt t.

2. Das innere Hidden-Neuron hat eine rekurrente Verbindung zu sich selbst mit Gewicht -1. Sein Aktivierungswert zum Zeitpunkt t sei mit h_t bezeichnet. 
Für h_t gilt: h_t = f(x_t + (-1) * h_{t-1}), wobei f die Sigmoidfunktion ist.
Da alle Biases 0 sind, taucht kein Bias-Term in der Berechnung auf.

3. Für den Aktivierungswert des Ausgabeneurons o_t zum Zeitpunkt t gilt:
o_t = f(1 * h_t), da das Gewicht der Verbindung vom Hidden-Neuron zum Ausgabeneuron 1 ist.

4. Wir beginnen zum Zeitpunkt t=0 und berechnen die Aktivierungen rekursiv bis zum letzten Zeitschritt T.
Dabei ist h_0 = 0, da kein Aktivierungswert aus einem vorherigen Zeitschritt vorliegt.

5. In jedem Zeitschritt t berechnen wir zuerst h_t aus dem aktuellen Eingabewert x_t und dem Aktivierungswert h_{t-1} des vorherigen Zeitschritts. 
Dann berechnen wir den Ausgabewert o_t aus h_t.

6. Der gesuchte Ausgabewert ist o_T, der Aktivierungswert des Ausgabeneurons im letzten Zeitschritt T.

Ohne konkrete Zahlenwerte für die Eingabesequenz lässt sich o_T nicht exakt bestimmen. Die Berechnung erfolgt aber nach dem beschriebenen Schema, indem in jedem Zeitschritt t der Aktivierungswert h_t des Hidden-Neurons aus dem aktuellen Input x_t und dem vorherigen Aktivierungswert h_{t-1} berechnet wird, und daraus dann der Ausgabewert o_t. Dieses Vorgehen wird rekursiv bis zum letzten Zeitschritt T durchgeführt.





****************************************************************************************
****************************************************************************************




Answer to Question 1-4
a. Zur Trainingszeit sind die Netzwerkeingaben eines RNN-basierten Sprachmodells, das mit Teacher Forcing trainiert wird, die tatsächlichen Wörter oder Token der Zielsequenz (Ground Truth). Das bedeutet, bei jedem Zeitschritt wird dem Netzwerk das korrekte Wort aus der Zielsequenz als Eingabe gegeben, unabhängig von der Vorhersage des Netzwerks im vorherigen Zeitschritt.

b. Zur Inferenzzeit sind die Netzwerkeingaben eines RNN-basierten Sprachmodells die vom Netzwerk selbst generierten Wörter oder Token. Das bedeutet, bei jedem Zeitschritt wird die Vorhersage des Netzwerks aus dem vorherigen Zeitschritt als Eingabe für den aktuellen Zeitschritt verwendet. Das Netzwerk generiert also schrittweise die Ausgabesequenz, indem es seine eigenen Vorhersagen als Eingabe für die nächsten Schritte nutzt.





****************************************************************************************
****************************************************************************************




Answer to Question 1-5
Hier sind die Antworten zu den Fragen:

Ausgabe Dimensionen, Anzahl Parameter und Dimensionen des receptive fields für jede Schicht:

Input: 
- Ausgabe Dimensionen: 32 x 32 x 3
- Anzahl Parameter: 0 
- Dimensionen des receptive fields: 1

CONV3-8:
- Ausgabe Dimensionen: 30 x 30 x 8
- Anzahl Parameter: (3 * 3 * 3 + 1) * 8 = 224
- Dimensionen des receptive fields: 3

Leaky ReLU: 
- Ausgabe Dimensionen: 30 x 30 x 8
- Anzahl Parameter: 0
- Dimensionen des receptive fields: 3

POOL-2:
- Ausgabe Dimensionen: 15 x 15 x 8 
- Anzahl Parameter: 0
- Dimensionen des receptive fields: 6

BATCHNORM:
- Ausgabe Dimensionen: 15 x 15 x 8
- Anzahl Parameter: 2 * 8 = 16 (Skalierung und Verschiebung pro Kanal)
- Dimensionen des receptive fields: 6

CONV3-16:
- Ausgabe Dimensionen: 13 x 13 x 16
- Anzahl Parameter: (3 * 3 * 8 + 1) * 16 = 1168
- Dimensionen des receptive fields: 10

Leaky ReLU:
- Ausgabe Dimensionen: 13 x 13 x 16
- Anzahl Parameter: 0
- Dimensionen des receptive fields: 10

POOL-2:
- Ausgabe Dimensionen: 6 x 6 x 16
- Anzahl Parameter: 0 
- Dimensionen des receptive fields: 22

FLATTEN:
- Ausgabe Dimensionen: 576
- Anzahl Parameter: 0
- Dimensionen des receptive fields: 22

FC-10:
- Ausgabe Dimensionen: 10
- Anzahl Parameter: (576 + 1) * 10 = 5770
- Dimensionen des receptive fields: 22

Die Gesamtzahl der Parameter im Netzwerk beträgt 224 + 16 + 1168 + 5770 = 7178.





****************************************************************************************
****************************************************************************************




Answer to Question 2-1
Hier sind meine Antworten zu den Aussagen über Gradientenabstieg:

[falsch] tanh wird in der Regel gegenüber sigmoid bevorzugt, weil bei diesem das Vanishing Gradient Problem nicht auftritt
[wahr] Vanishing gradient sorgt für langsameres Lernen in späten layern als in frühen layern
[wahr] Leaky ReLU leidet weniger unter dem vanishing gradient Problem als sigmoid
[wahr] Xavier Initialisierung kann dabei helfen das vanishing gradient Problem zu vermeiden
[falsch] Keine der obigen Aussagen





****************************************************************************************
****************************************************************************************




Answer to Question 2-2
1. (wahr) Die Größe der Convolution Kernels kann die Größe des rezeptiven Feldes erhöhen, wenn wir ein Convolutional Neural Network verwenden.

2. (falsch) Die Anzahl der Kanäle in den Convolution Kernels hat keinen direkten Einfluss auf die Größe des rezeptiven Feldes.

3. (falsch) Die Aktivierungsfunktion in jedem Layer beeinflusst nicht die Größe des rezeptiven Feldes.

4. (wahr) Die Größe der Pooling Layers kann die Größe des rezeptiven Feldes erhöhen, da Pooling die räumliche Auflösung reduziert und somit effektiv das rezeptive Feld vergrößert.





****************************************************************************************
****************************************************************************************




Answer to Question 2-3
Hier sind meine Antworten auf die Frage:

[X] Wahr
[ ] Falsch

Bei einer logistischen Regression ohne Bias-Term führt eine Division des Gewichtsvektors W durch 2 zu keiner Veränderung der Testgenauigkeit. 

Begründung: Ohne Bias ist die Entscheidungsgrenze der logistischen Regression eine Hyperebene, die durch den Ursprung geht. Eine Skalierung des Gewichtsvektors ändert zwar die Werte der vorhergesagten Wahrscheinlichkeiten, aber nicht die resultierende Klassifikation auf der einen oder anderen Seite der Hyperebene. Daher bleibt die Testgenauigkeit unverändert, wenn man den Gewichtsvektor durch eine Konstante wie 2 dividiert.





****************************************************************************************
****************************************************************************************




Answer to Question 2-4
Hier sind meine Antworten zu den Fragen:

1. f(x) = min(2,x)
   (falsch) Diese Funktion ist nach oben beschränkt und daher keine geeignete Aktivierungsfunktion.

2. f(x) = 3x + 1  
   (wahr) Eine lineare Funktion wie diese kann als Aktivierungsfunktion verwendet werden, auch wenn sie selten eingesetzt wird.

3. f(x) = min(x, 0.5x) if x < 0; f(x) =  min(x, 0.5x) if x >= 0
   (falsch) Diese Funktion ist nicht monoton steigend und daher ungeeignet als Aktivierungsfunktion. 

4. f(x) = min(x, 0.1x) if x < 0; f(x) =  max(x, 0.1x) if x >= 0
   (wahr) Dies entspricht der ReLU-Funktion (Rectified Linear Unit) mit Steigung 0.1 für negative Werte. ReLU ist eine sehr häufig verwendete Aktivierungsfunktion in neuronalen Netzen.





****************************************************************************************
****************************************************************************************




Answer to Question 2-5
Hier sind meine Antworten zu den Fragen:

Welche der folgenden Ansätze kann Overfitting reduzieren?

[wahr] Data Augmentation
[wahr] Dropout 
[falsch] Batch Normalization
[falsch] Benutzung von Adam anstelle von SGD

Data Augmentation und Dropout sind beides effektive Techniken, um Overfitting in neuronalen Netzen zu reduzieren:

- Data Augmentation erweitert den Trainingsdatensatz künstlich durch zufällige Transformationen (z.B. Rotation, Skalierung, Spiegelung). Dadurch wird das Netz robuster und generalisiert besser auf ungesehene Daten.

- Dropout deaktiviert während des Trainings zufällig einen Teil der Neuronen. Das verhindert, dass sich das Netz zu sehr an spezifische Muster in den Trainingsdaten anpasst.

Batch Normalization hilft zwar die Konvergenz zu beschleunigen und die Netzperformance zu verbessern, reduziert aber nicht direkt Overfitting.

Die Wahl des Optimierers (Adam vs. SGD) hat keinen direkten Einfluss auf Overfitting. Beide können in Kombination mit Regularisierungstechniken wie L2-Regularisierung verwendet werden, um Overfitting zu reduzieren.





****************************************************************************************
****************************************************************************************




Answer to Question 2-6
Hier sind meine Antworten zu den Fragen:

[] falsch
[] falsch 
[wahr] im Betrag verringern, die Polarität erhalten bleiben
[] falsch

Erklärung: Wenn der Gradient durch die Sigmoid-Funktion zurückfließt, wird er sich immer im Betrag verringern, während die Polarität erhalten bleibt. Dies liegt daran, dass die Ableitung der Sigmoid-Funktion y = f(x) gleich y * (1-y) ist. Da sowohl y als auch (1-y) Werte zwischen 0 und 1 annehmen, ist das Produkt y*(1-y) immer kleiner oder gleich 0,25. Dadurch wird der Gradient bei jedem Durchlauf durch die Sigmoid-Funktion abgeschwächt, behält aber sein Vorzeichen bei.





****************************************************************************************
****************************************************************************************




Answer to Question 3-1
a) Damit der attention head $h$ in Schicht $l$ im Dekodierungsschritt $n+1$ am meisten zu Position $n$ attended, muss gelten:

$$(x^l_n)^T W^{l,h}_Q (W^{l,h}_K)^T x^l_n > (x^l_n)^T W^{l,h}_Q (W^{l,h}_K)^T x^l_i \quad \forall i \in \{1, \dots, n-1\}$$

Das heißt, das Skalarprodukt (die Kompatibilität) zwischen dem Query-Vektor an Position $n$ und dem Key-Vektor an Position $n$ muss größer sein als die Skalarprodukte zwischen dem Query-Vektor an Position $n$ und allen anderen Key-Vektoren an Positionen $i < n$ in der Sequenz.

b) Um die Aufgabe der "Previous token heads" für beliebige Eingabesequenzen erfüllen zu können, benötigt die Transformer-Architektur die Positionsenkodierungen (positional encodings) zusätzlich zum eigentlichen self-attention Mechanismus. 

Die Positionsenkodierungen fügen Informationen über die relative oder absolute Position jedes Tokens in der Sequenz hinzu. Ohne diese hätte das Modell kein Konzept von Reihenfolge und Positionen und könnte nicht lernen, bevorzugt auf das direkt vorhergehende Token zu attenden. Die Positionsenkodierungen ermöglichen es dem Modell, positionsabhängige Berechnungen in der self-attention durchzuführen.





****************************************************************************************
****************************************************************************************




Answer to Question 3-2
a) Damit beim greedy decoding im Dekodierungsschritt $n+1$ das Token $t_{k+1}$ als nächstes prädiziert wird, muss gelten:

$\text{softmax}(W_O^{L,h} \cdot v^{L,h}_{n+1})_{t_{k+1}} > \text{softmax}(W_O^{L,h'} \cdot v^{L,h'}_{n+1})_{t'}$ für alle $h' \neq h$ und alle $t' \neq t_{k+1}$.

Das heißt, die Ausgabewahrscheinlichkeit für das Token $t_{k+1}$ muss für den Attention Head $h$ in der letzten Schicht $L$ größer sein als die Ausgabewahrscheinlichkeiten aller anderen Tokens für alle anderen Attention Heads.

b) Damit der Attention Head $h$ in Schicht $l$ im Dekodierungsschritt $n+1$ am meisten zur Position $k+1$ attended, muss gelten:

$\text{softmax}((x^l_{n+1} W_Q^{l,h}) \cdot (x^l_{k+1} W_K^{l,h})^T) > \text{softmax}((x^l_{n+1} W_Q^{l,h}) \cdot (x^l_{j} W_K^{l,h})^T)$ für alle $j \neq k+1$.

Das heißt, der Attention Score zwischen der Query an Position $n+1$ und dem Key an Position $k+1$ muss größer sein als die Attention Scores zwischen der Query an $n+1$ und allen anderen Keys.

c) Nein, ein Transformer mit nur einem Attention Layer kann diese Bedingung nicht für beliebige Sequenzen erfüllen. 

Der Grund ist, dass die Attention Scores nur von den aktuellen Eingaben $x^l_i$ abhängen. Um zu erkennen, ob $t_k = t_n$ gilt, müsste das Modell aber die gesamte bisherige Sequenz berücksichtigen. Mit nur einem Layer ist das nicht möglich, da die Eingaben $x^l_i$ keine Information über die vorherigen Tokens $t_1, ..., t_{i-1}$ enthalten.

d) - Im gleichen Layer gibt es keinen Kommunikationskanal zwischen verschiedenen Attention Heads. Jeder Head arbeitet unabhängig.

- In aufeinanderfolgenden Layern werden die Ausgaben $z^l_i$ des vorherigen Layers als Eingaben $x^{l+1}_i$ an den nächsten Layer weitergegeben. Dieser "Kommunikationskanal" wird durch die Konkatenation und lineare Transformation der Attention Head Outputs $z^{l,h}_i = W^{l,h}_O v^{l,h}_i$ befüllt. Was davon im nächsten Layer "gelesen" wird, hängt von den Query-, Key- und Value-Matrizen $W^{l+1,h}_Q$, $W^{l+1,h}_K$, $W^{l+1,h}_V$ ab.

e) Eine mögliche Sequenz von Attention-Operationen:

- In Layer 1 attended ein Head an Position $n+1$ zur Position $n$ (erkennt $t_n$) und ein anderer zur Position $k$ (erkennt $t_k$). 
- Durch Addition/Subtraktion der Positionsembeddings in den Ausgaben $z^{1,h}_i$ "kommunizieren" diese Heads, dass $t_k = t_n$ gilt.
- In Layer 2 kann der Head $h$ diese Information nutzen, um gezielt zur Position $k+1$ zu attenden und so $t_{k+1}$ als nächstes Token vorherzusagen.





****************************************************************************************
****************************************************************************************




Answer to Question 4-1
Um das Embedding $E(s_k)$ für das Eingabetoken $s_k$ als Matrix-Vektor-Multiplikation zu beschreiben, gehen wir wie folgt vor:

1. Die vektorielle Eingabe für das $i$-te Vokabularwort $s_k$ ist ein One-Hot-Vektor $v_k \in \mathbb{R}^{|V|}$. Dieser Vektor hat die Dimension der Vokabulargröße $|V|$ und enthält eine 1 an der Stelle $i$, die dem Index des Wortes $s_k$ im Vokabular entspricht. Alle anderen Elemente des Vektors sind 0.

2. Dieser One-Hot-Vektor $v_k$ wird nun mit der Embedding-Matrix $W_E \in \mathbb{R}^{|V| \times d}$ multipliziert. Durch die Matrix-Vektor-Multiplikation $W_E \cdot v_k$ wird effektiv die $i$-te Zeile der Embedding-Matrix $W_E$ ausgewählt, die der Worteinbettung (Word Embedding) $x_k \in \mathbb{R}^d$ für das Wort $s_k$ entspricht.

Zusammengefasst lässt sich das Embedding $E(s_k)$ für das Eingabetoken $s_k$ als folgende Matrix-Vektor-Multiplikation beschreiben:

$E(s_k) = x_k = W_E \cdot v_k$

wobei $v_k$ der One-Hot-Vektor für das Wort $s_k$ ist und $W_E$ die Embedding-Matrix darstellt.





****************************************************************************************
****************************************************************************************




Answer to Question 4-2
a) Damit wir das Netz mithilfe von Gradientenabstieg trainieren können, muss die Abbildung $g$ differenzierbar sein.

b) Der Gradient $\\nabla l$ bezüglich $W_E$ lässt sich mit der Kettenregel berechnen:

$\\frac{\\partial l}{\\partial W_E} = \\frac{\\partial l}{\\partial f(w)} \\cdot \\frac{\\partial f(w)}{\\partial E(w)} \\cdot \\frac{\\partial E(w)}{\\partial W_E}$

$= \\frac{\\partial \\mathcal{L}(f(w), t)}{\\partial f(w)} \\cdot \\frac{\\partial g(E(w))}{\\partial E(w)} \\cdot \\frac{\\partial E(w)}{\\partial W_E}$

$= \\frac{\\partial \\mathcal{L}}{\\partial f(w)} \\cdot \\frac{\\partial g}{\\partial E(w)} \\cdot \\frac{\\partial E(w)}{\\partial W_E}$

c) Für $i \\neq k$ gilt: $\\frac{\\partial l}{\\partial w_{ij}} = 0$, da das Eingabewort $w$ nur von der $k$-ten Zeile der Embedding-Matrix $W_E$ abhängt, nicht von den anderen Zeilen.

d) Die Erkenntnis aus c) hat folgende Auswirkungen auf die Komplexität:

Vorwärtspass: Es muss nur die Embedding-Zeile für das aktuelle Eingabewort $w$ geladen und berechnet werden, nicht die gesamte Embedding-Matrix. Das reduziert Speicher- und Rechenaufwand.

Rückwärtspass: Der Gradient muss nur für die Zeile der Embedding-Matrix berechnet werden, die dem Eingabewort $w$ entspricht. Gradienten für andere Zeilen sind 0. Das spart ebenfalls Speicher und Rechenzeit, da nicht die gesamte Matrix aktualisiert werden muss.





****************************************************************************************
****************************************************************************************




