diff --git a/semester3/numcs/numcs-summary.pdf b/semester3/numcs/numcs-summary.pdf index c189f11..fc432ac 100644 Binary files a/semester3/numcs/numcs-summary.pdf and b/semester3/numcs/numcs-summary.pdf differ diff --git a/semester3/numcs/numcs-summary.tex b/semester3/numcs/numcs-summary.tex index 3f5b892..5705ab5 100644 --- a/semester3/numcs/numcs-summary.tex +++ b/semester3/numcs/numcs-summary.tex @@ -13,6 +13,7 @@ \setLang{de} \setup{Numerical Methods for Computer Science} +\newcommand{\innumpy}{\fhlc{Cyan}{In \texttt{numpy}}\smallhspace} \begin{document} \startDocument diff --git a/semester3/numcs/parts/00_introduction/02_matrix-multiplication.tex b/semester3/numcs/parts/00_introduction/02_matrix-multiplication.tex index b484382..a614611 100644 --- a/semester3/numcs/parts/00_introduction/02_matrix-multiplication.tex +++ b/semester3/numcs/parts/00_introduction/02_matrix-multiplication.tex @@ -6,7 +6,7 @@ \subsection{Rechnen mit Matrizen} Wie in Lineare Algebra besprochen, ist das Resultat der Multiplikation einer Matrix $A \in \C^{m \times n}$ und einer Matrix $B \in \C^{n \times p}$ ist eine Matrix $AB = \in \C^{m \times p}$ -\fhlc{Cyan}{In NumPy} haben wir folgende Funktionen: +\innumpy haben wir folgende Funktionen: \begin{itemize} \item \verb|b @ a| (oder \verb|np.dot(b, a)| oder \verb|np.einsum('i,i', b, a)| für das Skalarprodukt \item \verb|A @ B| (oder \verb|np.einsum('ik,kj->ij', )|) für das Matrixprodukt @@ -59,7 +59,7 @@ Sei $A = ab^\top$. Dann gilt $y = Ax \Leftrightarrow y = a(b^\top x)$, was dasse \inlineex Für zwei Matrizen $A, B \in \R^{n \times p}$ mit geringem Rang $p \ll n$, dann kann mithilfe eines Tricks die Rechenzeit von \verb|np.triu(A @ B.T) @ x| von $\tco{pn^2}$ auf $\tco{pn}$ reduziert werden. Die hier beschriebene Operation berechnet $\text{Upper}(AB^\top) x$ wobei $\text{Upper}(X)$ das obere Dreieck der Matrix $X$ zurück gibt. Wir nennen diese Matrix hier $R$. -Wir können in NumPy den folgenden Ansatz verwenden, um die Laufzeit zu verringern: +\innumpy können wir den folgenden Ansatz verwenden, um die Laufzeit zu verringern: Da die Matrix $R$ eine obere Dreiecksmatrix ist, ist das Ergebnis die Teilsummen von unserem Umgekehrten Vektor $x$, also können wir mit \verb|np.cumsum(x[::-1], axis=0)[::-1]| die Kummulative Summe berechnen. Das \verb|[::-1]| dient hier lediglich dazu, den Vektor $x$ umzudrehen, sodass das richtige Resultat entsteht. Die vollständige Implementation sieht so aus: @@ -80,7 +80,9 @@ Die vollständige Implementation sieht so aus: \setcounter{all}{21} -\fancydef{Kronecker-Produkt} Das Kronecker-Produkt ist eine $(ml) \times (nk)$-Matrix, für $A \in \R^{m \times n}$ und $B \in \R^{l \times k}$, die wir in NumPy einfach mit \verb|np.kron(A, B)| berechnen können (ist jedoch nicht immer ideal): +\fancydef{Kronecker-Produkt} Das Kronecker-Produkt ist eine $(ml) \times (nk)$-Matrix, für $A \in \R^{m \times n}$ und $B \in \R^{l \times k}$. + +\innumpy können wir dieses einfach mit \verb|np.kron(A, B)| berechnen (ist jedoch nicht immer ideal): \begin{align*} A \otimes B := \begin{bmatrix} diff --git a/semester3/numcs/parts/01_interpolation/00_polynomial/01_monome.tex b/semester3/numcs/parts/01_interpolation/00_polynomial/01_monome.tex index 28cd03c..d870ad6 100644 --- a/semester3/numcs/parts/01_interpolation/00_polynomial/01_monome.tex +++ b/semester3/numcs/parts/01_interpolation/00_polynomial/01_monome.tex @@ -36,4 +36,4 @@ Zur Auswertung von $p(x)$ kann man direkt die Matrix-darstellung nutzen, oder ef \fancydef{Horner Schema} $p(x) = (x \ldots x ( x (\alpha_n x + \alpha_{n-1}) + \ldots + \alpha_1) + \alpha_0)$ -\fhlc{Cyan}{In NumPy} \verb|polyfit| liefert die direkte Auswertung, \verb|polyval| wertet Polynome via Horner-Schema aus. (Gemäss Script, in der Praxis sind diese Funktionen \verb|deprecated|) +\innumpy liefert \verb|polyfit| die direkte Auswertung, \verb|polyval| wertet Polynome via Horner-Schema aus. (Gemäss Script, in der Praxis sind diese Funktionen \verb|deprecated|) diff --git a/semester3/numcs/parts/01_interpolation/01_trigonometric/02_fft.tex b/semester3/numcs/parts/01_interpolation/01_trigonometric/02_fft.tex index 2dc0d65..6a99cd1 100644 --- a/semester3/numcs/parts/01_interpolation/01_trigonometric/02_fft.tex +++ b/semester3/numcs/parts/01_interpolation/01_trigonometric/02_fft.tex @@ -38,5 +38,5 @@ Wir formen die Fourier-Transformation um für den ersten Fall ($N = 2m$): Der zweite Fall ist einfach eine rekursive Weiterführung des ersten Falls, bei welchem dann das $m$ kontinuierlich weiter dividiert wird bis zum Trivialfall mit einer $1 \times 1$-Matrix. -\fhlc{Cyan}{In NumPy} gibt es die Funktionen \texttt{np.fft.fft} (Vorwärts FFT), \texttt{np.fft.ifft} (Rückwärts FFT). +\innumpy gibt es die Funktionen \texttt{np.fft.fft} (Vorwärts FFT), \texttt{np.fft.ifft} (Rückwärts FFT). \texttt{scipy.fft} liefert dieselben Funktionen und sie sind oft etwas schneller als die von \texttt{numpy} diff --git a/semester3/numcs/parts/01_interpolation/01_trigonometric/05_dft-chebyshev.tex b/semester3/numcs/parts/01_interpolation/01_trigonometric/05_dft-chebyshev.tex index c32fdd3..29f5afb 100644 --- a/semester3/numcs/parts/01_interpolation/01_trigonometric/05_dft-chebyshev.tex +++ b/semester3/numcs/parts/01_interpolation/01_trigonometric/05_dft-chebyshev.tex @@ -43,7 +43,7 @@ Auf Seite 102 im Skript findet sich auch eine effiziente Implementation dessen. \inlineremark Die Formel in Satz 2.4.16 (und in der eben erwähnten Implementierung) sind nichts anderes als eine Version der DCT (Discrete Cosine Transform). Dies ist eine günstigere, aber beschränktere Variante der DFT, mit der nur reellwertige, gerade Funktionen interpoliert werden können. -\fhlc{Cyan}{In NumPy} benutzen wir \texttt{scipy.fft.dct}. Dazu müssen die Mesungen in den Punkten $x_j = \cos\left( (j + 0.5) \cdot \frac{\pi}{N} \right)$ +\innumpy benutzen wir \texttt{scipy.fft.dct}. Dazu müssen die Mesungen in den Punkten $x_j = \cos\left( (j + 0.5) \cdot \frac{\pi}{N} \right)$ \inlineremark Die Chebyshev-Koeffizienten $c_j$ können folgendermassen berechnet werden: \rmvspace diff --git a/semester3/numcs/parts/01_interpolation/02_piece-wise/00_intro.tex b/semester3/numcs/parts/01_interpolation/02_piece-wise/00_intro.tex index a6f81ba..7cf74b3 100644 --- a/semester3/numcs/parts/01_interpolation/02_piece-wise/00_intro.tex +++ b/semester3/numcs/parts/01_interpolation/02_piece-wise/00_intro.tex @@ -1,4 +1,5 @@ % Lecture: \chi here are used as RELU function! +\subsection{Stückweise Lineare Interpolation} Globale Interpolation (also Interpolation auf dem ganzen Intervall $]-\infty, \infty[$) funktioniert nur dann gut, wenn: \rmvspace \begin{enumerate}[label=(\alph*), noitemsep] diff --git a/semester3/numcs/parts/01_interpolation/02_piece-wise/01_hermite-interpolation.tex b/semester3/numcs/parts/01_interpolation/02_piece-wise/01_hermite-interpolation.tex index fa619ec..ab07b3a 100644 --- a/semester3/numcs/parts/01_interpolation/02_piece-wise/01_hermite-interpolation.tex +++ b/semester3/numcs/parts/01_interpolation/02_piece-wise/01_hermite-interpolation.tex @@ -18,7 +18,7 @@ und deren Ableitung $\psi'(t) = t(3t - 2)$. Mit demselben Variablenwechsel müss \end{align*} Die Interpolationsfunktion ist dann einfach die Summe $s_j(x) = p_j(x) + q_j(x) \mediumhspace \text{für } x \in [x_{j - 1}, x_j]$ -\fhlc{Cyan}{In Numpy} verwendet man \texttt{scipy.interpolate.Akima1DInterpolator} oder \texttt{PchipInterpolator}, welcher ``formerhaltender'' ist, +\innumpy verwendet man \texttt{scipy.interpolate.Akima1DInterpolator} oder \texttt{PchipInterpolator}, welcher ``formerhaltender'' ist, also wenn eine Funktion lokal monoton ist, so ist der Interpolant dort auch monoton. Bei anderen Interpolationsmethoden ist dies nicht garantiert (so auch nicht beim \texttt{Akima1DInterpolator}) diff --git a/semester3/numcs/parts/01_interpolation/02_piece-wise/02_splines.tex b/semester3/numcs/parts/01_interpolation/02_piece-wise/02_splines.tex index e69de29..bc0191b 100644 --- a/semester3/numcs/parts/01_interpolation/02_piece-wise/02_splines.tex +++ b/semester3/numcs/parts/01_interpolation/02_piece-wise/02_splines.tex @@ -0,0 +1,16 @@ +\newsectionNoPB +\subsection{Splines} +\begin{definition}[]{Raum der Splines} + Sei $[a, b] \subseteq \R$ ein Intervall, sei $\mathcal{G} = \{ a = x_0 < x_1 < \ldots < x_N = b \}$ und sei $d \geq 1 \in \N$. + Die Menge + \begin{align*} + \mathcal{S}_{d, \mathcal{G}} = \{ s \in C^{d - 1}[a, b], \smallhspace s_j := s_{|[x_{j - 1}, x_j]|} \text{ ist ein polynom von Grad höchstens } d \} + \end{align*} + ist die Menge aller auf $[a, b]$ $(d - 1)$ mal stetig ableitbaren Funktionen, die auf $\mathcal{G}$ aus stückweisen Polynomen von Grad höchtens $d$ bestehen + und wir der Raum der Splines vom Grad $d$, oder der Ordnung $(d + 1)$ genannt +\end{definition} + +\inlineremark Obige Definition ist undefiniert für $d = 0$, aber $\mathcal{S}_{d, \mathcal{G}}$ kann als die Menge der stückweise Konstanten Funktionen betrachtet werden. +Im Vergleich zu den Kubischen Hermite-Interpolanten sind die Kubischen-Splines (für $d = 3$) \textit{zweimal} Ableitbar statt nur \textit{einmal} + +\inlineremark $\dim(\mathcal{S}_{d, \mathcal{G}}) = N + d$. Es werden oft kubische Splines in Anwendungen verwendet