{
 "cells": [
  {
   "attachments": {},
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "# Woche 10 #\n",
    "\n",
    "Diese Wochen beschäftigen wir uns mit Matrizen und Vektoren.\n",
    "In diesem Notebook rechnen wir ein paar (Teil)aufgaben aus dem ÜB."
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "'''IMPORTS'''\n",
    "import os;\n",
    "import sys; \n",
    "\n",
    "# NOTE: need this to force jupyter to reload imports:\n",
    "for key in list(sys.modules.keys()):\n",
    "    if key.startswith('src.'):\n",
    "        del sys.modules[key];\n",
    "\n",
    "os.chdir(os.path.dirname(_dh[0]));\n",
    "sys.path.insert(0, os.getcwd());\n",
    "\n",
    "from src.thirdparty.maths import *;\n",
    "from src.thirdparty.misc import *;\n",
    "from src.thirdparty.render import *;\n",
    "from src.maths.diagrams import *;\n",
    "\n",
    "np.random.seed(8007253); # zur Wiederholbarkeit"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "'''BEISPIEL-SIGNAL'''\n",
    "n = 100;\n",
    "u = np.zeros((n,), dtype=complex);\n",
    "u[8] = -0.7\n",
    "u[58] = 1j * sqrt(2);\n",
    "\n",
    "display_signal(u, 'Beispiel eines Vektors als Signal dargestellt');"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "'''SEMINARAUFGABE 10.4 a)'''\n",
    "n = 3;\n",
    "t = linspace(0, n-1, n);\n",
    "i, j = np.meshgrid(t, t);\n",
    "theta = 2*pi * i * j / n;\n",
    "\n",
    "# definiere die Matrix F_n + die Vektoren u_nk\n",
    "F_n = (1/sqrt(n)) * exp(-1j * theta);\n",
    "u_n = [ (1/sqrt(n)) * exp(1j * theta[:, k]) for k in range(n) ];\n",
    "\n",
    "print(dedent(\n",
    "    f'''\n",
    "    Matrix:\n",
    "\n",
    "    F_{n} = \\n{np.round(F_n, 3)}\n",
    "    '''\n",
    "));\n",
    "print('');\n",
    "\n",
    "# NOTE: Programmiersprachen können nicht exakt berechnen.\n",
    "# Darum entstehen winzige Fehler, die sich durch Runden entfernen lassen.\n",
    "print('Matrix-Vektor-Produkte:');\n",
    "for k in range(n):\n",
    "    result = F_n @ u_n[k];\n",
    "    print(dedent(\n",
    "        f'''\n",
    "\n",
    "              u_{{n {k}}} = {np.round(u_n[k], 3)}\n",
    "        F_n · u_{{n {k}}} = {np.round(result, 3)}\n",
    "        '''\n",
    "    ));"
   ]
  },
  {
   "attachments": {},
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "## Seminaraufgabe 10.4 b) ##\n",
    "\n",
    "Für $i\\in\\{0,1,\\ldots,n-1\\}$ ist die $i$-te von $\\mathcal{F}_{n}\\,u_{n,k}$\n",
    "\n",
    "$$\n",
    "    (\\mathcal{F}_{n}\\,u_{n,k})_{i}\n",
    "    = \\sum_{j=0}^{n-1}\n",
    "        (\\mathcal{F}_{n})_{ij}\\,(u_{n,k})_{j}\n",
    "    = \\sum_{j=0}^{n-1}\n",
    "        \\tfrac{1}{\\sqrt{n}}\n",
    "        \\exp(-\\imath\\tfrac{2\\pi\\,ij}{n})\n",
    "        \\cdot\n",
    "        \\tfrac{1}{\\sqrt{n}}\n",
    "        \\exp(\\imath\\tfrac{2\\pi\\,kj}{n})\n",
    "    = \\frac{1}{n}\\sum_{j=0}^{n-1}\n",
    "        \\underbrace{\n",
    "            \\exp(\\imath\\tfrac{2\\pi\\,(k-i)j}{n})\n",
    "        }_{= r^{j}}\n",
    "$$\n",
    "\n",
    "wobei $r \\colonequals \\exp(\\imath\\tfrac{2\\pi\\,(k-i)}{n})$.\n",
    "Wir haben, dass\n",
    "    $r = 1$\n",
    "    $\\Leftrightarrow$\n",
    "        $\\tfrac{k-i}{n} \\in \\Z$\n",
    "    $\\Leftrightarrow$\n",
    "        $i = k$,\n",
    "da $0\\leq i,k \\leq n-1$.\n",
    "<br>\n",
    "Es gilt außerdem $r^{n} = \\exp(\\imath 2\\pi\\,(k-i)) = 1$.\n",
    "<br>\n",
    "Aus der o.s. Berechnung erhält man also\n",
    "\n",
    "$$\n",
    "    (\\mathcal{F}_{n}\\,u_{n,k})_{i}\n",
    "    = \\tfrac{1}{n}\\displaystyle\\sum_{j=0}^{n-1}r^{j}\n",
    "    = \\tfrac{1}{n}\n",
    "        \\begin{cases}\n",
    "            \\displaystyle\\sum_{j=0}^{n-1}1 &: &i = k\\\\\n",
    "            \\frac{1 - r^{n}}{1 - r} &: &\\text{sonst}\\\\\n",
    "        \\end{cases}\n",
    "    = \\tfrac{1}{n}\n",
    "        \\begin{cases}\n",
    "            n &: &i = k\\\\\n",
    "            \\frac{1 - 1}{1 - r} &: &\\text{sonst}\\\\\n",
    "        \\end{cases}\n",
    "    = \\delta_{ik}.\n",
    "$$\n",
    "\n",
    "Darum $\n",
    "    \\mathcal{F}_{n}\\,u_{n,k}\n",
    "    = \\left(\\begin{matrix}\n",
    "        0\\\\\n",
    "        0\\\\\n",
    "        \\vdots\\\\\n",
    "        1\\\\\n",
    "        \\vdots\\\\\n",
    "        0\\\\\n",
    "    \\end{matrix}\\right)\n",
    "    \\begin{matrix}\n",
    "        \\\\\n",
    "        \\\\\n",
    "        \\\\\n",
    "        \\leftarrow k\\\\\n",
    "        \\\\\n",
    "        \\\\\n",
    "    \\end{matrix}\n",
    "    = \\mathbf{e}_{k}\n",
    "$.\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "'''SEMINARAUFGABE 10.4 d)'''\n",
    "n = 4;\n",
    "t = linspace(0, n-1, n);\n",
    "i, j = np.meshgrid(t, t);\n",
    "theta = 2*pi * i * j / n;\n",
    "\n",
    "# definiere die Matrix F_n + die Vektoren u_nk\n",
    "F_n = (1/sqrt(n)) * exp(-1j * theta);\n",
    "u_n = [ (1/sqrt(n)) * exp(1j * theta[:, k]) for k in range(n) ];\n",
    "\n",
    "# Eingabe des Vektors:\n",
    "F_mal_u = np.asarray([100, -3, 0, -3]); # = F_n @ u\n",
    "\n",
    "'''\n",
    "NOTE: Folgende Koeffizienten wurden falsch erraten.\n",
    "TODO: Wie lauten die richtigen Werte? -> Aufgabe!\n",
    "'''\n",
    "c = [10,10,40,50];\n",
    "\n",
    "# Aufschreibung des Signals »bzgl. der harmonischen Basis«:\n",
    "# u = c[0]u_n[0] + c[1]u_n[1] + c[2]u_n[2] + c[3]u_n[3]\n",
    "u_guess = sum([ c[k] * u_n[k] for k in range(n) ]);\n",
    "\n",
    "# Anzeige der Lösung:\n",
    "display_signal(u_guess, 'Geschätztes Signal');\n",
    "\n",
    "# Verifikation von Lösung:\n",
    "print(dedent(\n",
    "    f'''\n",
    "    %error := ‖u_guess –  u‖ / ‖u‖\n",
    "            = ‖F_n · (u_guess – u)‖ / ‖F_n · u‖\n",
    "                ... wieso?? [Stichwort: unitär]\n",
    "            = ‖F_n · u_guess –  F_n · u‖ / ‖F_n · u‖\n",
    "            = {linalg.norm(F_n @ u_guess - F_mal_u)/linalg.norm(F_mal_u):.2%}\n",
    "    '''\n",
    "));\n"
   ]
  }
 ],
 "metadata": {
  "kernelspec": {
   "display_name": "Python 3",
   "language": "python",
   "name": "python3"
  },
  "language_info": {
   "codemirror_mode": {
    "name": "ipython",
    "version": 3
   },
   "file_extension": ".py",
   "mimetype": "text/x-python",
   "name": "python",
   "nbconvert_exporter": "python",
   "pygments_lexer": "ipython3",
   "version": "3.10.8"
  }
 },
 "nbformat": 4,
 "nbformat_minor": 2
}
