{
 "cells": [
  {
   "cell_type": "raw",
   "id": "f1724c85",
   "metadata": {},
   "source": [
    "---\n",
    "notebook-links: false\n",
    "---"
   ]
  },
  {
   "cell_type": "markdown",
   "id": "75a11f86",
   "metadata": {},
   "source": [
    "# Das Typsystem von Julia\n",
    "\n",
    "Man kann umfangreiche Programme in Julia schreiben, ohne auch nur eine einzige Typdeklaration verwenden zu müssen. Das ist natürlich Absicht und soll die Arbeit der Anwender vereinfachen.\n",
    "\n",
    "Wir blicken jetzt trotzdem mal unter die Motorhaube.\n",
    "\n",
    "## Die Typhierarchie\n",
    "\n",
    "Das Typsystem hat die Struktur eines Baums, dessen Wurzel der Typ `Any` ist. Mit den Funktionen `subtypes()` und `supertype()` kann man den Baum erforschen. Sie zeigen alle Kinder bzw. die Mutter eines Knotens an.\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "f3f47e9d",
   "metadata": {},
   "outputs": [],
   "source": [
    "subtypes(Int64)"
   ]
  },
  {
   "cell_type": "markdown",
   "id": "3cb68ade",
   "metadata": {},
   "source": [
    "Das Ergebnis ist eine leere Liste von Typen. `Int64` ist ein sogenannter **konkreter Typ** und hat keine Untertypen.\n",
    "\n",
    "Wir klettern jetzt mal die Typhierarchie auf diesem Ast nach oben bis zur Wurzel (Informatiker-Bäume stehen bekanntlich immer auf dem Kopf).\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "c7c10d75",
   "metadata": {},
   "outputs": [],
   "source": [
    "supertype(Int64)"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "15b4e8d6",
   "metadata": {},
   "outputs": [],
   "source": [
    "supertype(Signed)"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "2c62f342",
   "metadata": {},
   "outputs": [],
   "source": [
    "supertype(Integer)"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "ee7eb511",
   "metadata": {},
   "outputs": [],
   "source": [
    "supertype(Real)"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "9ab37b54",
   "metadata": {},
   "outputs": [],
   "source": [
    "supertype(Number)"
   ]
  },
  {
   "cell_type": "markdown",
   "id": "d5fe3447",
   "metadata": {},
   "source": [
    "Das wäre übrigens auch schneller gegangen: Die Funktion `supertypes()` (mit Plural-s) zeigt alle Vorfahren an.\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "895d4570",
   "metadata": {},
   "outputs": [],
   "source": [
    "supertypes(Int64)"
   ]
  },
  {
   "cell_type": "markdown",
   "id": "79a45ce0",
   "metadata": {},
   "source": [
    "Nun kann man sich die Knoten angucken:\n",
    "\n",
    "<!-- 12A0366C:../notebooks/nb-types.ipynb#nb3 |  | echo:false,warning:false,asis:true,eval:false -->\n",
    "\n",
    "Mit einer kleinen rekursiven Funktion kann man schnell einen ganzen (Unter-)Baum ausdrucken:  \n",
    "\n",
    "<!-- 12A0366C:../notebooks/nb-types.ipynb#nb1 |  | echo:false,warning:false,asis:true,eval:false -->\n",
    "\n",
    "::::{.content-hidden unless-format=\"xxx\"}\n",
    "\n",
    "...und natürlich gibt es da auch ein Julia-Paket:\n",
    "\n",
    "<!-- 12A0366C:../notebooks/nb-types.ipynb#nb2 |  | echo:false,warning:false,asis:true,eval:false -->\n",
    "\n",
    ":::\n",
    "\n",
    "\n",
    "::: {.content-visible when-format=\"html\"}\n",
    "![](../images/TypeTree2.png)\n",
    ":::\n",
    "\n",
    "::: {.content-visible when-format=\"pdf\"}\n",
    "![The type tree of numbers](../images/TypeTree2.png) {width=50%}\n",
    ":::\n",
    "\n",
    "### Abstrakte und Konkrete Typen\n",
    "\n",
    "- Ein Objekt hat immer einen **konkreten** Typ. \n",
    "- Komkrete Typen haben keine Untertypen mehr, sie sind immer „Blätter“ des Baumes.\n",
    "- Abstrakte Typen können in der Definition von Funktionstypen, Argumenttypen, Elementtypen von zusammengesetzten Typen,... verwendet werden\n",
    "\n",
    "https://github.com/carstenbauer/JuliaCologne21/blob/master/Day1/1_types_and_dispatch.ipynb\n",
    "\n",
    "Zum Deklarieren und Testen der \"Abstammung\" gibt es einen eigenen Operator:\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "e300c9a9",
   "metadata": {},
   "outputs": [],
   "source": [
    "Int64 <: Number "
   ]
  }
 ],
 "metadata": {
  "kernelspec": {
   "display_name": "Julia 1.8.5",
   "language": "julia",
   "name": "julia-1.8"
  }
 },
 "nbformat": 4,
 "nbformat_minor": 5
}
