{
 "cells": [
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "# Auslegungsrechnung: Lokomotive für Hängeförderbahn\n",
    "\n",
    "Diese Rechnung untersucht, wie schwer eine Lokomotive sein muss, um über Reibschluss eine Zugkraft von 100 N aufzubringen. Zusätzlich wird das nötige Antriebsmoment pro Rolle berechnet. Im Anschluss kann aus der Fahrgeschwindigkeit die Drehzahl der Rollen sowie die benötigte Antriebsleistung ermittelt werden. Erste Annahmen für Batteriekapazität werden getroffen.\n",
    "\n",
    "## Annahmen\n",
    "- Zugkraftbedarf (Anfahren): **100 N**\n",
    "- Anfahrbeschleuniugung: **0.1-0.2 m/s^2**\n",
    "- Zugkraftbedarf (Konstantfahrt): **10 N**\n",
    "\n",
    "- Reibwert Gummi auf Aluminium: variabel, realistisch: **0.3–0.6**\n",
    "- Rollendurchmesser: z. B. **80 mm**\n",
    "- Anzahl angetriebener Rollen: z. B. **2**\n"
   ]
  },
  {
   "cell_type": "markdown",
   "id": "fe11045c",
   "metadata": {},
   "source": [
    "## Mathematische Grundlagen\n",
    "\n",
    "Die Lokomotive bewegt sich auf einem Aluminiumprofil mit zwei 45° geneigten Flanken. Die Zugkraft wird über Reibung zwischen den angetriebenen Gummirädern und dem Profil erzeugt. Die folgenden Gleichungen beschreiben die physikalische Auslegung.\n",
    "\n",
    "---\n",
    "\n",
    "### 1. Gewicht der Lokomotive\n",
    "\n",
    "Aus der Gleichgewichtsbedingung bei Reibung auf 2× 45°-Flanken:\n",
    "\n",
    "$$\n",
    "F_{\\text{N,gesamt}} = 2 \\cdot \\left( \\frac{G}{2} \\cdot \\cos(45^\\circ) \\right) = \\frac{G}{\\sqrt{2}}\n",
    "$$\n",
    "\n",
    "Maximale Reibkraft:\n",
    "\n",
    "$$\n",
    "F_{\\text{Reib}} = \\mu \\cdot F_{\\text{N,gesamt}} = \\mu \\cdot \\frac{G}{\\sqrt{2}}\n",
    "$$\n",
    "\n",
    "Gleichsetzen mit Zugkraft:\n",
    "\n",
    "$$\n",
    "F_{\\text{Zug}} = \\mu \\cdot \\frac{G}{\\sqrt{2}} \\Rightarrow G = \\frac{F_{\\text{Zug}} \\cdot \\sqrt{2}}{\\mu}\n",
    "$$\n",
    "\n",
    "Masse der Lokomotive:\n",
    "\n",
    "$$\n",
    "m = \\frac{G}{g} = \\frac{F_{\\text{Zug}} \\cdot \\sqrt{2}}{\\mu \\cdot g}\n",
    "$$\n",
    "\n",
    "---\n",
    "\n",
    "### 2. Drehmoment an den Antriebsrollen\n",
    "\n",
    "Bei gleichmäßiger Verteilung auf $n_{\\text{Rollen}}$ Rollen mit Durchmesser $d$:\n",
    "\n",
    "$$\n",
    "F_{\\text{Rolle}} = \\frac{F_{\\text{Zug}}}{n_{\\text{Rollen}}}\n",
    "$$\n",
    "\n",
    "$$\n",
    "M = F_{\\text{Rolle}} \\cdot \\frac{d}{2}\n",
    "$$\n",
    "\n",
    "Gesamtmoment:\n",
    "\n",
    "$$\n",
    "M_{\\text{gesamt}} = n_{\\text{Rollen}} \\cdot M = F_{\\text{Zug}} \\cdot \\frac{d}{2}\n",
    "$$\n",
    "\n",
    "---\n",
    "\n",
    "### 3. Drehzahl der Rollen\n",
    "\n",
    "Bei Zielgeschwindigkeit $v$ und Rollendurchmesser $d$:\n",
    "\n",
    "$$\n",
    "n = \\frac{v}{\\pi \\cdot d} \\cdot 60\n",
    "$$\n",
    "\n",
    "---\n",
    "\n",
    "### 4. Leistung am Antrieb\n",
    "\n",
    "Die mechanische Leistung berechnet sich zu:\n",
    "\n",
    "$$\n",
    "P = M_{\\text{gesamt}} \\cdot \\omega = M_{\\text{gesamt}} \\cdot \\left( \\frac{2\\pi \\cdot n}{60} \\right)\n",
    "$$\n",
    "\n",
    "---\n",
    "\n",
    "### 5. Batteriekapazität (theoretisch)\n",
    "\n",
    "Bei Betriebsdauer $t$ (in Stunden) und Spannung $U$:\n",
    "\n",
    "$$\n",
    "Q_{\\text{Wh}} = P \\cdot t\n",
    "$$\n",
    "\n",
    "$$\n",
    "Q_{\\text{Ah}} = \\frac{Q_{\\text{Wh}}}{U}\n",
    "$$\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 189,
   "metadata": {},
   "outputs": [],
   "source": [
    "import numpy as np\n",
    "import matplotlib.pyplot as plt\n",
    "\n",
    "\n",
    "# Konstanten\n",
    "g = 9.81  # Erdbeschleunigung in m/s²\n",
    "\n",
    "# Eingabeparameter\n",
    "f_zug_anfaren = 100  # Zugkraftbedarf max. in N\n",
    "f_zug_konstant = 10  # Zugkraftbedarf konst. in N\n",
    "fahrgeschwindigkeit_ms = 1.3  # Fahrgeschwindigkeit in m/s\n",
    "mu_min = 0.3  # minimaler Reibwert\n",
    "mu_max = 0.7  # maximaler Reibwert\n",
    "rollendurchmesser_mm = 50  # Rollendurchmesser in mm\n",
    "anzahl_rollen = 2  # Anzahl angetriebener Rollen\n",
    "\n",
    "\n",
    "# Zusätzliche Parameter für Plots\n",
    "betriebszeit_min = 1 # Minimale Betriebszeit in Stunden für Batterieplot\n",
    "betriebszeit_max = 8 # Maximale Betriebszeit in Stunden für Batterieplot\n",
    "betriebsspannung_v = 24 # Angenommene Betriebsspannung in Volt\n",
    "\n",
    "def berechne_lokgewicht(f_zug, mu_eff):\n",
    "    \"\"\"Berechnet das notwendige Lokgewicht für eine gegebene effektive Reibung\"\"\"\n",
    "    G = (f_zug * np.sqrt(2)) / mu_eff  # Gewichtskraft in N, sqrt(2) aufgrund der 45° geneigten Lauffläche der Rollen\n",
    "    m = G / g  # Masse in kg\n",
    "    return m\n",
    "\n",
    "def berechne_drehmoment(f_zug, rollendurchmesser_mm, anzahl_rollen):\n",
    "    \"\"\"Berechnet das Drehmoment pro Rolle in Nm\"\"\"\n",
    "    r = rollendurchmesser_mm / 2000  # Radius in Meter (Durchmesser / 2 / 1000)\n",
    "    f_pro_rolle = f_zug / anzahl_rollen\n",
    "    M_pro_rolle = f_pro_rolle * r\n",
    "    return M_pro_rolle\n",
    "\n",
    "def berechne_drehzahl(fahrgeschwindigkeit_ms, rollendurchmesser_mm):\n",
    "    \"\"\"Berechnet die Drehzahl der Rollen in Umdrehungen pro Minute (RPM).\"\"\"\n",
    "    rollenradius_m = (rollendurchmesser_mm / 2) / 1000  # Radius in Metern\n",
    "    drehzahl_rad_s = fahrgeschwindigkeit_ms / rollenradius_m\n",
    "    drehzahl_rpm = drehzahl_rad_s * (60 / (2 * np.pi))\n",
    "    return drehzahl_rpm\n",
    "\n",
    "\n",
    "def berechne_leistung(drehmoment_pro_rolle, drehzahl_rpm, anzahl_rollen):\n",
    "    \"\"\"Berechnet die benötigte Antriebsleistung.\"\"\"\n",
    "    drehzahl_rad_s = drehzahl_rpm * (2 * np.pi / 60)\n",
    "    gesamt_drehmoment = drehmoment_pro_rolle * anzahl_rollen\n",
    "    leistung_watt = gesamt_drehmoment * drehzahl_rad_s\n",
    "    return leistung_watt\n",
    "\n",
    "def berechne_batteriekapazitaet(leistung_watt, betriebszeit_h, betriebsspannung_v, sicherheitsfaktor=1.2):\n",
    "    \"\"\"Berechnet die benötigte Batteriekapazität in Amperestunden (Ah).\"\"\"\n",
    "    energie_wh = leistung_watt * betriebszeit_h\n",
    "    kapazitaet_ah = (energie_wh / betriebsspannung_v) * sicherheitsfaktor\n",
    "    return kapazitaet_ah\n"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "## Plot: Lokgewicht über Reibwert\n",
    "Dieser Plot zeigt, wie stark das notwendige Lokgewicht vom angenommenen Reibwert abhängt. Reibwerte im oberen Bereich sollten angestrebt werden."
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 190,
   "metadata": {},
   "outputs": [
    {
     "data": {
      "image/png": "[encoded data, 36036 characters]",
      "text/plain": [
       "<Figure size 500x300 with 1 Axes>"
      ]
     },
     "metadata": {},
     "output_type": "display_data"
    }
   ],
   "source": [
    "# Beispielwerte\n",
    "f_zug_anfaren = 100  # N\n",
    "mu_werte = np.linspace(mu_min, mu_max, 50)\n",
    "lokgewichte = [berechne_lokgewicht(f_zug_anfaren, mu) for mu in mu_werte]\n",
    "\n",
    "# Plot\n",
    "plt.figure(figsize=(5, 3))\n",
    "plt.plot(mu_werte, lokgewichte, label='Benötigtes Lokgewicht', color='blue')\n",
    "plt.xlabel(\"Effektiver Reibwert (μ)\")\n",
    "plt.ylabel(\"Erforderliches Lokgewicht (kg)\")\n",
    "plt.title(\"Einfluss des Reibwerts auf das Lokgewicht für 100 N Zugkraft\")\n",
    "plt.grid(True)\n",
    "plt.legend()\n",
    "plt.tight_layout()\n",
    "plt.show()"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "## Beispielrechnung mit festen Parametern"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 191,
   "metadata": {},
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "=== Typischer Mischbetrieb (95 % Konstantfahrt, 5 % Anfahren) ===\n",
      "Mittlere Antriebsleistung: 18.85 W\n",
      "Benötigtes Drehmoment im Anfahren: 1.25 Nm\n",
      "Benötigtes Drehmoment in Konstanntfahrt: 0.12 Nm\n",
      "Energieverbrauch pro Meter: 0.004 Wh/m\n",
      "Benötigte Masse (aus Spitzenlast): 28.83 kg\n",
      "Drehzahl der Rollen: 496.6 RPM\n"
     ]
    }
   ],
   "source": [
    "# Einheitlicher Reibwert\n",
    "mu = 0.5\n",
    "\n",
    "# Beschleunigungsbedarf\n",
    "a = 0.1 # m/s^2\n",
    "\n",
    "# Anteil der Betriebsmodi\n",
    "anteil_anfahren = 0.05\n",
    "anteil_konstant = 0.95\n",
    "\n",
    "# Berechnungen\n",
    "gewicht_anfahren = berechne_lokgewicht(f_zug_anfaren, mu)\n",
    "\n",
    "# Wir verwenden dieselbe Drehzahl für beide Fälle\n",
    "drehzahl_rpm = berechne_drehzahl(fahrgeschwindigkeit_ms, rollendurchmesser_mm)\n",
    "\n",
    "# Drehmomente und Leistungen\n",
    "drehmoment_anfahren = berechne_drehmoment(f_zug_anfaren, rollendurchmesser_mm, anzahl_rollen)\n",
    "leistung_anfahren = berechne_leistung(drehmoment_anfahren, drehzahl_rpm, anzahl_rollen)\n",
    "\n",
    "drehmoment_konstant = berechne_drehmoment(f_zug_konstant, rollendurchmesser_mm, anzahl_rollen)\n",
    "leistung_konstant = berechne_leistung(drehmoment_konstant, drehzahl_rpm, anzahl_rollen)\n",
    "\n",
    "# Gemittelte Leistung\n",
    "leistung_mittel = anteil_anfahren * leistung_anfahren + anteil_konstant * leistung_konstant\n",
    "\n",
    "# Energieverbrauch pro Meter (Wh/m)\n",
    "energieverbrauch_wh_pro_m = leistung_mittel / fahrgeschwindigkeit_ms / 3600  # (W / m/s) * (1/3600) = Wh/m\n",
    "\n",
    "# Batteriebedarf für typische Betriebszeiten\n",
    "betriebszeiten = np.linspace(betriebszeit_min, betriebszeit_max, 100)\n",
    "kapazitaet_ah_mittel = [berechne_batteriekapazitaet(leistung_mittel, t, betriebsspannung_v) for t in betriebszeiten]\n",
    "\n",
    "# Ausgabe\n",
    "print(\"=== Typischer Mischbetrieb (95 % Konstantfahrt, 5 % Anfahren) ===\")\n",
    "print(f\"Mittlere Antriebsleistung: {leistung_mittel:.2f} W\")\n",
    "print(f\"Benötigtes Drehmoment im Anfahren: {drehmoment_anfahren:.2f} Nm\")\n",
    "print(f\"Benötigtes Drehmoment in Konstanntfahrt: {drehmoment_konstant:.2f} Nm\")\n",
    "print(f\"Energieverbrauch pro Meter: {energieverbrauch_wh_pro_m:.3f} Wh/m\")\n",
    "print(f\"Benötigte Masse (aus Spitzenlast): {gewicht_anfahren:.2f} kg\")\n",
    "print(f\"Drehzahl der Rollen: {drehzahl_rpm:.1f} RPM\")\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 192,
   "id": "d894f650",
   "metadata": {},
   "outputs": [
    {
     "data": {
      "image/png": "[encoded data, 55620 characters]",
      "text/plain": [
       "<Figure size 1000x500 with 1 Axes>"
      ]
     },
     "metadata": {},
     "output_type": "display_data"
    }
   ],
   "source": [
    "import numpy as np\n",
    "import matplotlib.pyplot as plt\n",
    "\n",
    "# Parameter\n",
    "m = gewicht_anfahren  # Masse in kg\n",
    "a = 0.1  # Beschleunigung in m/s²\n",
    "\n",
    "\n",
    "# Abgeleitete Größen\n",
    "t_beschleunigung = fahrgeschwindigkeit_ms / a  # Zeit bis Zielgeschwindigkeit erreicht ist\n",
    "F_beschleunigung = m * a  # Trägheitskraft in N\n",
    "\n",
    "# Zeitvektor\n",
    "t = np.linspace(0, t_beschleunigung + 2, 1000)\n",
    "\n",
    "# Geschwindigkeit über die Zeit\n",
    "v = np.where(t <= t_beschleunigung, a * t, fahrgeschwindigkeit_ms)\n",
    "\n",
    "# Momentane Leistung\n",
    "P_momentan = np.where(\n",
    "    t <= t_beschleunigung,\n",
    "    (F_beschleunigung + f_zug_konstant) * v,\n",
    "    f_zug_konstant * fahrgeschwindigkeit_ms\n",
    ")\n",
    "\n",
    "# Plot\n",
    "plt.figure(figsize=(10, 5))\n",
    "plt.plot(t, P_momentan, label=\"Momentanleistung [W]\", color=\"crimson\")\n",
    "plt.axvline(t_beschleunigung, linestyle=\"--\", color=\"gray\", label=\"Ende Beschleunigung\")\n",
    "plt.axhline(f_zug_konstant * fahrgeschwindigkeit_ms, linestyle=\":\", color=\"green\", label=\"Leistung bei Konstantfahrt\")\n",
    "plt.xlabel(\"Zeit [s]\")\n",
    "plt.ylabel(\"Leistung [W]\")\n",
    "plt.title(\"Momentanleistung während Anfahren und Konstantfahrt\")\n",
    "plt.grid(True)\n",
    "plt.legend()\n",
    "plt.tight_layout()\n",
    "plt.show()\n",
    "\n"
   ]
  }
 ],
 "metadata": {
  "kernelspec": {
   "display_name": ".venv",
   "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.13.3"
  }
 },
 "nbformat": 4,
 "nbformat_minor": 5
}
