\documentclass[11pt]{article} \input{style_guide.tex} \title{\textbf{\Huge Warum manche Probleme schwer sind}\\[0.6em] \large Ein Anfänger-Guide zu Komplexitätstheorie und Approximation\\[0.3em] \normalsize \textit{Analyse von Algorithmen und Komplexität} -- CAU Kiel, Sommersemester 2026} \author{} \date{} \begin{document} \maketitle \thispagestyle{empty} \begin{center} \itshape \large \glqq Manche Probleme lösen wir in Sekunden.\\ Bei anderen läuft der Computer bis zum Hitzetod des Universums.\\ Dieser Guide erklärt dir, woran das liegt -- und was man dann tut.\grqq \end{center} \vfill \noindent\textbf{An wen sich dieser Guide richtet.} An dich, wenn du gerade erst anfängst. Du brauchst keine Vorkenntnisse in Komplexitätstheorie. Was du brauchst: Neugier und die Bereitschaft, jedes Kapitel wirklich durchzuarbeiten -- nicht zu überfliegen. \medskip \noindent\textbf{Wie du liest.} Der Guide erzählt eine \emph{Geschichte}, keine Liste. Jedes Kapitel beginnt mit einer Frage, die sich aus dem vorigen ergibt. Die farbigen Kästen haben feste Rollen: \begin{center} \small \begin{tabular}{ll} \ding{72}~\textbf{Intuition} & die Idee in einfachen Worten\\ \ding{43}~\textbf{Analogie} & ein Bild aus dem Alltag\\ \ding{110}~\textbf{Definition} & die präzise Fassung\\ \ding{115}~\textbf{Satz} & ein Ergebnis mit kurzer Beweis\emph{idee}\\ \ding{108}~\textbf{Beispiel} & durchgerechnet, mit echten Zahlen\\ \ding{73}~\textbf{Aha} & die Pointe, die alles zusammenzieht\\ \ding{55}~\textbf{Stolperstein} & der Fehler, den fast alle machen\\ \ding{228}~\textbf{Zusammenhang} & wie es mit dem Rest verbunden ist\\ \ding{52}~\textbf{Selbst-Check} & prüfe dich, bevor du weiterliest\\ \end{tabular} \end{center} \medskip \noindent Am Ende verstehst du \emph{alle} Inhalte der Vorlesung und siehst, wie sie zusammenhängen. Der Schritt danach: Präsenz-, Haus- und Klausuraufgaben rechnen, um Routine zu bekommen. Dieser Guide gibt dir das \emph{Warum}, die Aufgaben das \emph{Können}. \vfill \newpage \tableofcontents \newpage % ################################################################## \section{Ein Problem, das sich wehrt} % ################################################################## \begin{ziel} Wir treffen ein Problem, das einfach aussieht -- und trotzdem jeden bekannten Computer in die Knie zwingt. Daran verstehst du, warum es eine ganze Theorie über \glqq schwere\grqq{} Probleme gibt. \end{ziel} \subsection{Freunde auf einer Party} Stell dir eine Party mit einigen Gästen vor. Manche kennen sich, manche nicht. Du fragst dich: \emph{Gibt es eine Gruppe von $k$ Gästen, die sich alle gegenseitig kennen?} Eine solche Gruppe, in der \emph{jeder jeden} kennt, nennen wir eine \emph{Clique}. Das lässt sich als \emph{Graph} zeichnen: Jeder Gast ist ein Punkt (ein \emph{Knoten}), und eine Linie (eine \emph{Kante}) zwischen zwei Punkten heißt \glqq die beiden kennen sich\grqq. \begin{bsp}{Eine Clique mit dem Auge finden} \setlength{\unitlength}{1cm} \begin{center} \begin{picture}(4,2.6)(-0.4,-0.3) \put(0,1){\circle*{0.13}}\put(-0.4,1){\small $1$} \put(1,2){\circle*{0.13}}\put(1,2.2){\small $2$} \put(2,1){\circle*{0.13}}\put(2.2,1.05){\small $3$} \put(1.4,0){\circle*{0.13}}\put(1.3,-0.4){\small $4$} \put(3,0.5){\circle*{0.13}}\put(3.2,0.4){\small $5$} \put(0,1){\line(1,1){1}} % 1-2 \put(0,1){\line(1,0){2}} % 1-3 \put(1,2){\line(1,-1){1}} % 2-3 \put(2,1){\line(-3,-5){0.6}} % 3-4 \put(2,1){\line(2,-1){1}} % 3-5 \end{picture} \end{center} Fünf Gäste. Die Gruppe $\{1,2,3\}$ ist eine Clique: 1--2, 1--3 und 2--3 sind alle da. Also kennen sich alle drei gegenseitig. Die Gruppe $\{2,3,4\}$ ist \emph{keine} Clique -- zwischen 2 und 4 fehlt die Kante. Es gibt hier keine Clique aus vier Gästen. \end{bsp} Bei fünf Gästen siehst du die Antwort sofort. Aber ein Computer \glqq sieht\grqq{} nicht. Er muss rechnen. Und ab ein paar hundert Gästen wird selbst für den schnellsten Rechner der Welt genau das zum Problem. \subsection{Der naive Weg -- und warum er explodiert} Wie würde ein Computer eine $k$-Clique suchen? Der naheliegende Weg: \emph{probiere alle Gruppen aus $k$ Gästen durch} und prüfe für jede, ob sich wirklich alle kennen. Das klingt vernünftig. Rechnen wir nach, wie viele Gruppen das sind. Bei $n$ Gästen und Gruppengröße $k = n/2$ gibt es \glqq $n$ über $n/2$\grqq{} viele Gruppen -- und das sind mindestens $2^{n/2}$. \begin{bsp}{Wie schnell $2^{n/2}$ wächst} \begin{center} \begin{tabular}{rrl} \toprule Gäste $n$ & Gruppen $\ge 2^{n/2}$ & anschaulich\\ \midrule $20$ & $\ge 1\,024$ & ein Wimpernschlag\\ $40$ & $\ge 1\,048\,576$ & eine Sekunde\\ $100$ & $\ge 2^{50} \approx 10^{15}$ & über einen Monat bei $10^9$/s\\ $200$ & $\ge 2^{100} \approx 10^{30}$ & länger als das Alter des Universums\\ \bottomrule \end{tabular} \end{center} Jeder zusätzliche Gast \emph{verdoppelt} ungefähr den Aufwand. Das ist der Unterschied zwischen \glqq machbar\grqq{} und \glqq unmöglich\grqq. \end{bsp} \begin{intuition} Wenn der Aufwand sich bei jedem weiteren Element \emph{verdoppelt}, sprechen wir von \emph{exponentiellem} Wachstum. Exponentielles Wachstum ist der natürliche Feind jeder Berechnung: Es macht schon mittelgroße Eingaben unlösbar. Kein schnellerer Rechner rettet dich -- du müsstest ihn selbst verdoppeln, nur um \emph{einen} Gast mehr zu schaffen. \end{intuition} \begin{satz}{Der naive Clique-Algorithmus ist exponentiell} Für $k = |V|/2$ braucht der naive Algorithmus mindestens $2^{|V|/2}$ Schritte.\\ \emph{Beweisidee:} Es gibt $\binom{n}{n/2} \ge 2^{n/2}$ Gruppen zu prüfen, und schon das Durchprobieren so vieler Gruppen kostet exponentiell viel Zeit. \end{satz} \subsection{Die Frage, um die es geht} Vielleicht ist der naive Weg einfach dumm. Vielleicht gibt es einen cleveren Trick, der die Clique \emph{schnell} findet, ohne alle Gruppen durchzuprobieren. Für das Cliquenproblem hat bis heute \emph{niemand} so einen Trick gefunden. Aber -- und das ist der Kern -- niemand hat auch \emph{bewiesen}, dass es keinen gibt. Diese Lücke zwischen \glqq wir kennen keinen schnellen Weg\grqq{} und \glqq es gibt keinen schnellen Weg\grqq{} ist der Ausgangspunkt der ganzen Vorlesung. \begin{aha} Die Komplexitätstheorie beantwortet nicht die Frage \glqq Wie löse ich dieses Problem schnell?\grqq. Sie beantwortet die tiefere Frage: \glqq Ist dieses Problem \emph{überhaupt} schnell lösbar -- oder gehört es zu einer Familie von Problemen, bei denen alle gemeinsam scheitern?\grqq \end{aha} \begin{selbstcheck} Bevor du weiterliest: Warum hilft ein doppelt so schneller Computer beim naiven Clique-Algorithmus fast nichts?\\[0.3em] \emph{Antwort:} Weil schon \emph{ein} Gast mehr den Aufwand verdoppelt. Der schnellere Computer verschafft dir also gerade genug für einen einzigen zusätzlichen Gast -- das Problem wächst schneller, als Hardware je aufholen kann. \end{selbstcheck} % ################################################################## \section{Was heißt eigentlich \glqq schnell\grqq?} % ################################################################## \begin{ziel} Wir machen \glqq schnell\grqq{} und \glqq langsam\grqq{} präzise. Am Ende hast du die erste wichtige Klasse verstanden: $\Pclass$, die Probleme, die wir effizient lösen können. \end{ziel} \subsection{Laufzeit hängt von der Eingabegröße ab} Ein Algorithmus ist nicht einfach \glqq schnell\grqq. Er ist schnell \emph{relativ zur Größe seiner Eingabe}. Zehn Zahlen zu sortieren ist leicht; zehn Milliarden zu sortieren dauert. Wir messen deshalb die \emph{Laufzeit als Funktion der Eingabelänge} $n$. \begin{defn}{Laufzeit} $T_A(x)$ ist die Anzahl der Rechenschritte von Algorithmus $A$ auf Eingabe $x$. Die \emph{Worst-Case-Laufzeit} bei Eingabelänge $n$ ist die schlimmste über alle Eingaben dieser Länge: \[ T_A(n) = \max\{\,T_A(x) \mid |x| = n\,\}. \] \end{defn} Wir schauen bewusst auf den \emph{schlechtesten} Fall. Ein Algorithmus, der \glqq meistens\grqq{} schnell ist, aber gelegentlich explodiert, ist keine verlässliche Garantie. \subsection{Polynomiell gegen exponentiell -- die entscheidende Grenze} Es gibt viele Wachstumsarten, aber die eine Grenze, auf die alles hinausläuft, ist: \emph{polynomiell} gegen \emph{exponentiell}. \begin{itemize} \item \emph{Polynomiell} heißt: die Laufzeit ist $O(n^d)$ für eine feste Zahl $d$ -- also $n$, $n^2$, $n^3$, \dots \item \emph{Exponentiell} heißt: etwas wie $2^n$, das sich bei jedem Schritt verdoppelt. \end{itemize} \begin{bsp}{Der Graben zwischen $n^3$ und $2^n$} \begin{center} \begin{tabular}{rrr} \toprule $n$ & $n^3$ (polynomiell) & $2^n$ (exponentiell)\\ \midrule $10$ & $1\,000$ & $1\,024$\\ $20$ & $8\,000$ & rund $1$ Million\\ $50$ & $125\,000$ & rund $10^{15}$\\ $100$ & $1\,000\,000$ & rund $10^{30}$\\ \bottomrule \end{tabular} \end{center} Bei $n = 10$ sind beide harmlos. Bei $n = 100$ ist $n^3$ immer noch eine Millionstel Sekunde -- $2^n$ dagegen jenseits von allem. \emph{Diese Kluft ist der Grund, warum wir polynomiell mit \glqq effizient\grqq{} gleichsetzen.} \end{bsp} \begin{intuition} \glqq Polynomiell = effizient\grqq{} ist eine \emph{Konvention}, kein Naturgesetz. Ein $n^{100}$-Algorithmus wäre praktisch nutzlos. Aber die Konvention funktioniert erstaunlich gut: Polynomielle Algorithmen aus der Praxis haben fast immer kleine Exponenten ($n$, $n^2$, $n^3$), und die Grenze \glqq polynomiell\grqq{} bleibt stabil, egal welchen realistischen Computer man zugrunde legt. \end{intuition} \begin{defn}{Die Klasse P} $\Pclass$ ist die Menge aller Entscheidungsprobleme, die ein Algorithmus in \emph{polynomieller} Zeit löst: \[ \Pclass = \{\, L \mid \exists\ \text{Algorithmus } A,\ T_A(n) = O(n^d),\ d = O(1),\ A \text{ löst } L \,\}. \] In Worten: die Probleme, die wir \emph{effizient} lösen können. \end{defn} Beispiele für Probleme in $\Pclass$: Sortieren, kürzeste Wege im Graphen (Dijkstra), minimale Spannbäume, das Finden eines Matchings. Für all das kennen wir schnelle, polynomielle Algorithmen. \subsection{Warum wir Probleme als Ja/Nein-Fragen schreiben} Ein technischer, aber wichtiger Punkt. Die Theorie behandelt fast immer \emph{Entscheidungsprobleme} -- Fragen mit Antwort \glqq Ja\grqq{} oder \glqq Nein\grqq. Statt \glqq Wie groß ist die größte Clique?\grqq{} fragt man: \glqq Gibt es eine Clique mit mindestens $k$ Knoten?\grqq \begin{analogie} Das ist wie die Frage \glqq Ist dieses Gewicht schwerer als 10\,kg?\grqq{} statt \glqq Wie schwer ist es genau?\grqq. Wenn du die Ja/Nein-Frage für jede Schranke beantworten kannst, kennst du am Ende auch den genauen Wert -- du tastest ihn ein. Deshalb ist die Entscheidungsvariante \glqq gleich schwer\grqq{} wie das Optimierungsproblem, aber viel einfacher zu vergleichen und zu klassifizieren. \end{analogie} Um über \glqq alle Probleme\grqq{} sauber reden zu können, kodiert man jede Eingabe als \emph{Wort} über einem Alphabet, und ein Problem wird zur \emph{Menge der Ja-Wörter}. \begin{defn}{Alphabet, Wort, Sprache, Entscheidungsproblem} \begin{itemize} \item Ein \emph{Alphabet} $\Sigma$ ist eine endliche Symbolmenge (z.\,B. $\{0,1\}$). $\Sigma^*$ sind alle endlichen Wörter darüber; $|x|$ ist die Länge von $x$. \item Eine \emph{Sprache} ist eine Teilmenge $L \subseteq \Sigma^*$. \item Ein \emph{Entscheidungsproblem} identifiziert man mit der Sprache $L$ seiner Ja-Instanzen: $A$ löst es, wenn $A(x) = 1$ für $x \in L$ und $A(x) = 0$ sonst. \end{itemize} \end{defn} Du musst diese Kodierbrille nicht ständig vor Augen haben. Merke dir nur: \emph{Ein Problem = die Menge seiner Ja-Eingaben.} Beim Cliquenproblem ist das die Menge aller Paare $(G, k)$, für die $G$ wirklich eine $k$-Clique besitzt. \begin{stolper} \textbf{Zahlen sind binär kodiert -- und dadurch \glqq riesig\grqq.} Eine Zahl $K$ hat als Eingabe nur die Länge $O(\log K)$ (ihre Ziffern), ist als \emph{Wert} aber exponentiell größer. Ein Algorithmus, der bis $K$ zählt, ist also \emph{nicht} polynomiell in der Eingabelänge. Genau daran hängt später, warum \problem{SubSet Sum} schwer ist und was \glqq pseudopolynomiell\grqq{} bedeutet. Behalte es im Hinterkopf. \end{stolper} \begin{selbstcheck} Ist ein Algorithmus mit Laufzeit $n^5$ \glqq effizient\grqq{} im Sinne der Theorie?\\[0.3em] \emph{Antwort:} Ja. $n^5$ ist polynomiell ($d = 5$ ist eine feste Zahl), also liegt das Problem in $\Pclass$. In der Praxis wäre $n^5$ vielleicht langsam -- aber die Theorie zieht die Grenze bei polynomiell gegen exponentiell, und auf dieser Skala ist $n^5$ klar auf der guten Seite. \end{selbstcheck} % ################################################################## \section{Prüfen ist leichter als Lösen} % ################################################################## \begin{ziel} Wir entdecken die vielleicht wichtigste Beobachtung der ganzen Theorie: Für viele schwere Probleme ist es zwar hart, eine Lösung zu \emph{finden} -- aber kinderleicht, eine vorgelegte Lösung zu \emph{prüfen}. Das führt uns zur Klasse $\NP$. \end{ziel} \subsection{Die Sudoku-Beobachtung} \begin{analogie} Ein schweres Sudoku zu \emph{lösen} kann dich eine halbe Stunde kosten. Aber wenn dir jemand ein ausgefülltes Gitter hinlegt und fragt \glqq stimmt das?\grqq, prüfst du es in einer Minute: jede Zeile, jede Spalte, jeder Block. \emph{Lösen ist schwer, Prüfen ist leicht.} Genau diese Asymmetrie steckt hinter $\NP$. \end{analogie} Übertragen auf die Clique: Eine Clique zu \emph{finden} ist mühsam. Aber wenn dir jemand eine Gruppe von Gästen nennt und behauptet \glqq die bilden eine Clique\grqq, prüfst du das schnell -- du schaust einfach nach, ob zwischen jedem Paar eine Kante liegt. Diese \glqq vorgelegte Lösung\grqq{} bekommt einen Namen: \emph{Zertifikat}. \subsection{Zertifikat und Verifizierer} \begin{defn}{Verifizierer und Zertifikat} Ein \emph{Verifizierer} für ein Problem $L$ ist ein Algorithmus $A$, der zwei Eingaben bekommt: die Instanz $x$ und einen \emph{Lösungsvorschlag} $c$. Er erfüllt \[ x \in L \quad\Longleftrightarrow\quad \text{es gibt ein } c \text{ mit } A(x,c) = 1. \] Das $c$ heißt \emph{Zertifikat} (oder Zeuge). Der Verifizierer ist \emph{polynomiell}, wenn er für jede Ja-Instanz ein Zertifikat gibt, das er in polynomieller Zeit prüft. \end{defn} Lies die Äquivalenz genau: Für eine \emph{Ja}-Instanz gibt es ein Zertifikat, das $A$ überzeugt. Für eine \emph{Nein}-Instanz gibt es \emph{kein} solches Zertifikat -- egal, was man $A$ vorlegt, er sagt Nein. \begin{defn}{Die Klasse NP} $\NP$ ist die Menge aller Probleme, die einen \emph{polynomiellen Verifizierer} besitzen. \end{defn} \begin{intuition} $\NP$ ist \glqq effizient \emph{überprüfbar}\grqq{} -- nicht \glqq effizient lösbar\grqq. Der Name ist Programm: Eine Lösung zu finden mag exponentiell teuer sein, aber \emph{hätte} man sie, könnte man sie billig kontrollieren. Das Zertifikat ist die abgekürzte Antwort auf \glqq und woher weiß ich, dass das stimmt?\grqq. \end{intuition} \begin{bsp}{Zertifikate für vier Probleme} \begin{center} \begin{tabular}{lll} \toprule Problem & Zertifikat $c$ & Prüfung in Polyzeit\\ \midrule $k$-\problem{Clique} & die Knotengruppe $C$ & alle Paare verbunden? $|C| \ge k$?\\ \problem{SAT} & eine Belegung $\psi$ & macht $\psi$ die Formel wahr?\\ \problem{Vertex Cover} & die Knotenmenge $C$ & jede Kante getroffen? $|C| \le k$?\\ \problem{SubSet Sum} & die Teilmenge $S$ & ist $\sum_{j \in S} c_j = K$?\\ \bottomrule \end{tabular} \end{center} In jeder Zeile ist das Zertifikat kurz (polynomiell lang) und die Prüfung einfach. Genau das macht diese Probleme zu Mitgliedern von $\NP$. \end{bsp} \subsection{Die zweite Brille: Raten} Es gibt eine zweite, gleichwertige Art, $\NP$ zu sehen -- über das \emph{Raten}. Stell dir einen Algorithmus vor, der an jeder Verzweigung \emph{gleichzeitig alle Möglichkeiten} ausprobieren darf. So ein Algorithmus heißt \emph{nichtdeterministisch}. \begin{intuition} Der nichtdeterministische Algorithmus arbeitet nach dem Muster: \emph{rate die Lösung, dann prüfe sie}. Er \glqq rät\grqq{} in Polynomialzeit eine Lösungskandidatin und prüft sie deterministisch. Er akzeptiert, wenn \emph{mindestens ein} Rateweg zu \glqq Ja\grqq{} führt. Für eine Nein-Instanz führt \emph{kein} Weg zum Ziel. \end{intuition} Formal beschreibt man das mit einer nichtdeterministischen Turingmaschine. Du musst die Maschine nicht auswendig können, aber einmal gesehen haben: \begin{defn}{Nichtdeterministische Turingmaschine (NDTM), knapp} Eine NDTM darf zu jedem Zustand-Symbol-Paar \emph{mehrere} (oder keine) Folgeschritte haben -- sie verzweigt. Sie \emph{akzeptiert} eine Eingabe, wenn \emph{irgendein} Rechenweg in einem Endzustand hält, und zwar nach polynomiell vielen Schritten. Hat sie überall höchstens einen Folgeschritt, ist sie gewöhnlich (deterministisch) -- das ist der Fall, der $\Pclass$ definiert. \end{defn} \begin{satz}{Beide Sichten beschreiben dasselbe $\NP$} Die Definition über Verifizierer und die über NDTMs ergeben genau dieselbe Klasse.\\ \emph{Beweisidee:} Die Folge der Rateentscheidungen einer NDTM \emph{ist} ein Zertifikat. Umgekehrt rät eine NDTM zuerst das Zertifikat und simuliert dann den Verifizierer. \glqq Raten\grqq{} und \glqq ein Zertifikat bekommen\grqq{} sind zwei Namen für dasselbe. \end{satz} \subsection{P steckt in NP -- und die Millionenfrage} \begin{satz}{$\Pclass \subseteq \NP$} Jedes effizient \emph{lösbare} Problem ist auch effizient \emph{überprüfbar}.\\ \emph{Beweisidee:} Wenn du ein Problem selbst schnell lösen kannst, brauchst du gar kein Zertifikat -- du ignorierst es und rechnest die Antwort direkt aus. Der Löser ist also ein (besonders fauler) Verifizierer. \end{satz} Die große offene Frage ist die \emph{Umkehrung}: Ist auch alles, was man schnell \emph{prüfen} kann, schnell \emph{lösbar}? Also gilt $\Pclass = \NP$? \begin{aha} Ob $\Pclass = \NP$ gilt, weiß bis heute niemand. Es ist eines der sieben Millennium-Probleme, mit einer Million Dollar Preisgeld. Die meisten Forscher glauben $\Pclass \ne \NP$ -- also dass Prüfen \emph{echt} leichter ist als Lösen. Beweisen konnte es keiner. \emph{Alles Folgende in diesem Guide -- NP-Vollständigkeit, ETH, Approximation -- ist der geschickte Umgang mit genau dieser Unwissenheit.} \end{aha} \begin{zushang} Halte die drei Begriffe auseinander, sie kommen ständig wieder: \begin{itemize} \item $\Pclass$ -- effizient \emph{lösbar} (finden ist leicht). \item $\NP$ -- effizient \emph{überprüfbar} (prüfen ist leicht). \item $\Pclass \subseteq \NP$ ist bewiesen; ob Gleichheit gilt, ist offen. \end{itemize} Im nächsten Kapitel bauen wir das Werkzeug, mit dem man Probleme \emph{innerhalb} von $\NP$ nach Schwierigkeit vergleicht -- ohne $\Pclass = \NP$ zu kennen. \end{zushang} \begin{selbstcheck} Warum ist \glqq $L$ hat einen polynomiellen Verifizierer\grqq{} \emph{nicht} dasselbe wie \glqq $L$ ist in Polynomialzeit lösbar\grqq?\\[0.3em] \emph{Antwort:} Der Verifizierer bekommt das Zertifikat schon \emph{geschenkt} und muss es nur prüfen. Der Löser hat niemanden, der ihm die Lösung vorlegt -- er muss sie selbst finden, und das kann exponentiell viele Kandidaten bedeuten. Prüfen startet einen Schritt weiter als Lösen. \end{selbstcheck} % ################################################################## \section{\glqq Mindestens so schwer wie\grqq{} -- Reduktionen} % ################################################################## \begin{ziel} Wir bauen das wichtigste Werkzeug der ganzen Theorie: die \emph{Reduktion}. Mit ihr vergleicht man Probleme nach Schwierigkeit -- ohne für eines von beiden einen Algorithmus zu kennen. Das klingt wie Zauberei, ist aber eine schlichte Idee. \end{ziel} \subsection{Ein Problem mit einem anderen lösen} Angenommen, du hast einen fertigen Löser für Problem $B$. Und du stehst vor Problem $A$, für das du keinen Löser hast. Wenn du jede $A$-Frage so \emph{umformen} kannst, dass der $B$-Löser sie beantwortet, dann hast du $A$ gelöst -- geschenkt, über den Umweg $B$. \begin{analogie} Du willst wissen, ob eine Strecke länger als eine Meile ist, hast aber nur ein Lineal in Kilometern. Kein Problem: Du rechnest \glqq länger als 1 Meile?\grqq{} um in \glqq länger als 1{,}609\,km?\grqq{} und misst das. Die \emph{Umrechnung} ist billig, das Messen erledigt das km-Lineal. Genau das ist eine Reduktion: \emph{billiges Umformen} plus \emph{fremder Löser}. \end{analogie} \begin{defn}{Polynomielle Reduktion $A \redp B$} Eine \emph{Reduktion} von $A$ auf $B$ ist eine Funktion $f$, die jede $A$-Eingabe $w$ in eine $B$-Eingabe $f(w)$ übersetzt, sodass \[ w \in A \quad\Longleftrightarrow\quad f(w) \in B. \] Sie ist \emph{polynomiell}, wenn $f$ in polynomieller Zeit berechenbar ist (dann ist $f(w)$ auch nur polynomiell groß). Schreibweise: $A \redp B$. \end{defn} Lies die Bedingung genau: $f$ muss \emph{Ja} auf \emph{Ja} und \emph{Nein} auf \emph{Nein} abbilden. Eine Ja-Instanz von $A$ wird zu einer Ja-Instanz von $B$ -- und eine Nein-Instanz von $A$ zu einer Nein-Instanz von $B$. Beide Richtungen. \begin{intuition} $A \redp B$ heißt: \glqq $B$ ist \emph{mindestens so schwer} wie $A$.\grqq{} Denn wer $B$ effizient lösen kann, löst damit auch $A$ effizient (erst $f$ rechnen, dann den $B$-Löser fragen). Die Schwierigkeit \glqq fließt\grqq{} entlang des Pfeils: Ist $A$ schwer, muss $B$ es auch sein. \end{intuition} \subsection{Die Richtung -- der Fehler, der alle Punkte kostet} \begin{stolper} \textbf{Die Reduktionsrichtung ist der häufigste und teuerste Fehler.} Du willst zeigen, dass ein \emph{neues} Problem $Y$ schwer ist. Dann reduzierst du ein \emph{bekannt schweres} Problem $X$ \emph{auf} $Y$, also $X \redp Y$ (\glqq bekannt $\redp$ neu\grqq). Die Reduktion nimmt eine $X$-Instanz und baut daraus eine $Y$-Instanz. \emph{Niemals} umgekehrt. \end{stolper} Warum diese Richtung? Weil du die Schwere von $X$ auf $Y$ \emph{übertragen} willst. \glqq $X \redp Y$\grqq{} bedeutet \glqq $Y$ mindestens so schwer wie $X$\grqq. Da $X$ schon als schwer bekannt ist, erbt $Y$ diese Schwere. Machst du es andersherum ($Y \redp X$), zeigst du nur \glqq $Y$ ist \emph{höchstens} so schwer wie das schwere $X$\grqq{} -- das sagt über $Y$ gar nichts aus. \begin{analogie} Du willst beweisen, dass ein neuer Gegner stark ist. Dann lässt du den \emph{amtierenden Champion} gegen ihn antreten und zeigst: Wer den Neuen besiegt, besiegt auch den Champion. Du schickst nicht den Neuen gegen einen Anfänger. \glqq Bekannt stark $\redp$ neu\grqq. \end{analogie} \subsection{Reduktionen lassen sich verketten} \begin{satz}{Transitivität} Gilt $A \redp B$ und $B \redp C$, dann auch $A \redp C$.\\ \emph{Beweisidee:} Schalte die beiden Umformungen hintereinander: erst $A \to B$, dann $B \to C$. Die Ausgabe der ersten ist polynomiell groß, also bleibt auch die Verkettung polynomiell. \end{satz} Das ist der Grund, warum wir gleich eine ganze \emph{Kette} von Reduktionen bauen können: Einmal $X$ als schwer bekannt, überträgt sich die Schwere Glied für Glied auf alle folgenden Probleme. \begin{selbstcheck} Du willst zeigen, dass \problem{Vertex Cover} schwer ist, und weißt, dass \problem{Clique} schwer ist. In welche Richtung reduzierst du?\\[0.3em] \emph{Antwort:} $\problem{Clique} \redp \problem{Vertex Cover}$ -- vom bekannt schweren \problem{Clique} auf das neue \problem{Vertex Cover}. So erbt \problem{Vertex Cover} die Schwere. Andersherum hättest du nichts gezeigt. \end{selbstcheck} % ################################################################## \section{Die härtesten Probleme} % ################################################################## \begin{ziel} Jetzt fassen wir die schwersten Probleme in $\NP$ mit einem Namen: \emph{NP-vollständig}. Wir sehen, warum es überhaupt ein \glqq erstes\grqq{} solches Problem gibt und warum ein einziger schneller Algorithmus für eines von ihnen die gesamte Landschaft zum Einsturz brächte. \end{ziel} \subsection{NP-schwer und NP-vollständig} Mit der Reduktion können wir \glqq am schwersten in $\NP$\grqq{} präzise machen: ein Problem, auf das sich \emph{alle} Probleme aus $\NP$ reduzieren lassen. \begin{defn}{NP-schwer, NP-vollständig} \begin{itemize} \item $L_0$ ist \emph{NP-schwer}, wenn sich \emph{jedes} Problem $L \in \NP$ auf $L_0$ reduzieren lässt: $L \redp L_0$ für alle $L \in \NP$. \item $L_0$ ist \emph{NP-vollständig}, wenn es NP-schwer ist \textbf{und} selbst in $\NP$ liegt. \end{itemize} \end{defn} \begin{intuition} Trenne die zwei Hälften sauber: \begin{itemize} \item \emph{NP-schwer} ist eine \textbf{untere} Schranke: \glqq mindestens so schwer wie alles in $\NP$\grqq. \item \emph{$\in \NP$} ist eine \textbf{obere} Schranke: \glqq nicht schwerer als $\NP$\grqq. \item \emph{NP-vollständig} = beides. Diese Probleme sind exakt die schwersten \emph{innerhalb} von $\NP$. \end{itemize} \end{intuition} \begin{stolper} NP-schwer heißt \emph{nicht} automatisch \glqq in $\NP$\grqq. Es gibt Probleme, die NP-schwer sind, aber \emph{außerhalb} von $\NP$ liegen -- das Halteproblem (Kapitel~\ref{sec:halt}) ist so eines. \glqq Schwer\grqq{} und \glqq überhaupt lösbar\grqq{} sind zwei verschiedene Achsen. \end{stolper} \subsection{Warum ein einziger Algorithmus alles verändern würde} \begin{satz}{NP-vollständig verbindet $\Pclass$ und $\NP$} Ist $L_0$ NP-vollständig, dann gilt: $\Pclass = \NP$ genau dann, wenn $L_0 \in \Pclass$.\\ \emph{Beweisidee:} Läge $L_0$ in $\Pclass$, so könnte man \emph{jedes} $L \in \NP$ lösen: erst die Reduktion $L \redp L_0$ rechnen, dann den schnellen $L_0$-Löser anwerfen. Also wäre ganz $\NP$ in $\Pclass$. \end{satz} \begin{aha} Das ist die Sprengkraft der NP-Vollständigkeit. Fände jemand für \emph{ein einziges} NP-vollständiges Problem einen polynomiellen Algorithmus, dann wären \emph{schlagartig alle} NP-Probleme effizient lösbar -- $\Pclass = \NP$. Umgekehrt: Solange das niemandem gelingt, ist ein NP-Vollständigkeitsbeweis das stärkste bekannte Indiz \glqq dieses Problem hat vermutlich keinen effizienten Algorithmus\grqq. \end{aha} \subsection{Das erste NP-vollständige Problem: Cook--Levin} Damit die Reduktionskette starten kann, braucht man \emph{ein} NP-vollständiges Problem \glqq von Hand\grqq -- ohne sich auf ein anderes stützen zu können. Das lieferten Cook und Levin. Das Problem heißt \problem{SAT}: Gegeben eine aussagenlogische Formel, gibt es eine Belegung der Variablen, die sie wahr macht? \begin{satz}{Cook (1971), Levin (1973)} \problem{SAT} ist NP-vollständig.\\ \emph{Beweisidee:} Man nimmt ein \emph{beliebiges} Problem $L \in \NP$ mit seiner ratenden Maschine und \glqq gießt\grqq{} deren Rechnung in eine Formel: Variablen beschreiben \glqq welcher Zustand zur Zeit $t$\grqq, \glqq was steht auf dem Band\grqq{} usw. Die Formel ist so gebaut, dass ihre \emph{erfüllenden Belegungen genau den akzeptierenden Rechenwegen entsprechen}. Also: $L$-Ja-Instanz $\iff$ Formel erfüllbar. Da $L$ beliebig war, ist \problem{SAT} schwer für ganz $\NP$. \end{satz} Du musst diesen Beweis nicht im Detail können. Wichtig ist die Rolle: \problem{SAT} ist der \emph{Anker}. Ab hier braucht man nie wieder \glqq alle $L \in \NP$\grqq{} zu betrachten. \subsection{Der Motor: das Vererbungskorollar} \begin{satz}{Vererbungskorollar} Ist $L_0$ bereits NP-vollständig, gilt $L_0 \redp L_1$, und liegt $L_1 \in \NP$, dann ist auch $L_1$ NP-vollständig.\\ \emph{Beweisidee:} Für jedes $L \in \NP$ gilt $L \redp L_0 \redp L_1$ (Transitivität). Also ist $L_1$ NP-schwer; zusammen mit $L_1 \in \NP$ ist es NP-vollständig. \end{satz} \begin{aha} Das ist das Arbeitspferd. Um ein neues Problem als NP-vollständig zu entlarven, brauchst du nur zwei Dinge: \begin{enumerate} \item eine \emph{Reduktion} von \emph{einem} bekannten NP-vollständigen Problem auf das neue, und \item den Nachweis, dass das neue Problem in $\NP$ liegt (Zertifikat angeben). \end{enumerate} Kein Wort mehr über \glqq alle $L \in \NP$\grqq. So wächst die Liste der NP-vollständigen Probleme Schritt für Schritt -- genau das machen wir im nächsten Kapitel. \end{aha} \begin{selbstcheck} Du zeigst $\problem{SAT} \redp Y$ und weist nach, dass $Y \in \NP$. Was folgt -- und welchen der beiden Teile darfst du auf keinen Fall vergessen?\\[0.3em] \emph{Antwort:} Es folgt: $Y$ ist NP-vollständig. Vergiss nie den Teil $Y \in \NP$. Ohne ihn hast du nur NP-\emph{Schwere} gezeigt, nicht Vollständigkeit -- $Y$ könnte sonst noch schwerer als $\NP$ sein. \end{selbstcheck} % ################################################################## \section{Der Problem-Zoo}\label{sec:zoo} % ################################################################## \begin{ziel} Wir gehen die Probleme der Vorlesung durch -- aber nicht als Liste zum Auswendig\-lernen, sondern als \emph{Familie}, die über Reduktionen zusammenhängt. Zu jedem: worum es geht, warum es schwer ist, woher die Schwere kommt. \end{ziel} \subsection{Die Landkarte: eine Kette ab SAT} Alle folgenden Probleme sind NP-vollständig. Der Beweis ist immer dasselbe Rezept (Vererbungskorollar): reduziere von einem schon bekannten Problem und zeige $\in \NP$. Der Pfeil $\redp$ heißt \glqq wird reduziert auf\grqq. \begin{center} \small \begin{tabular}{ccccc} & & $\boxed{\textbf{\problem{SAT}}}$ {\footnotesize (Cook--Levin)} & & \\[0.4em] $\swarrow$ & & $\downarrow$ & & $\searrow$ \\[0.4em] $\problem{3-SAT}$ & & $\problem{$k$-Clique}$ & & $\problem{3-DM}$ \\[0.4em] $\downarrow$ & & $\downarrow$ & & $\downarrow$ \\[0.4em] $\problem{$k$-Color}$ & & $\problem{IS},\ \problem{VC}$ & & $\problem{3-EC}$ \\[0.4em] $\downarrow$ & & & & $\downarrow$ \\[0.4em] $\problem{3-SAT}'\!\to\!\problem{HK}\!\to\!\problem{TSP}$ & & & & $\problem{SubSet Sum}$ \\[0.4em] & & & & $\downarrow$ \\[0.4em] & & & & $\problem{Partition}\to P\|\Cmax;\ \problem{Knapsack}$ \\ \end{tabular} \end{center} \begin{intuition} Halte dir beim Lesen immer die Frage vor Augen: \glqq Von welchem Nachbarn erbt dieses Problem seine Schwere?\grqq{} Das ist der rote Faden. Die Probleme sind nicht einzeln schwer -- sie sind \emph{gemeinsam} schwer, verbunden durch die Pfeile. \end{intuition} \subsection{Die Logik-Probleme} \begin{defn}{SAT und 3-SAT} \problem{SAT}: Gegeben eine Formel in \emph{konjunktiver Normalform} (KNF) -- also ein UND von Klauseln, jede Klausel ein ODER von Literalen ($x_j$ oder $\neg x_j$). Frage: gibt es eine erfüllende Belegung?\\ \problem{3-SAT}: dasselbe, aber jede Klausel hat höchstens 3 Literale. \end{defn} \begin{bsp}{SAT von Hand} $\alpha = (x_1 \vee x_{10}) \wedge (x_1 \vee \neg x_{10}) \wedge (x_{10})$. Die dritte Klausel erzwingt $x_{10} = \true$. Dann verlangt die zweite Klausel $x_1 = \true$. Beide gesetzt, ist auch die erste erfüllt. Also erfüllbar mit $x_1 = x_{10} = \true$. \end{bsp} \problem{SAT} ist der Anker (Cook--Levin). \problem{3-SAT} ist die \glqq handliche\grqq{} Version, von der aus fast alle weiteren Reduktionen starten -- kurze Klauseln sind leichter zu verbauen. \begin{zushang} $\problem{SAT} \redp \problem{3-SAT}$: Man spaltet jede lange Klausel mit Hilfsvariablen in eine Kette von 3er-Klauseln auf, ohne die Erfüllbarkeit zu ändern. Dadurch bleibt \problem{3-SAT} genauso schwer wie \problem{SAT}. \end{zushang} \subsection{Die Graph-Probleme und ihr Dreieck} Drei Probleme, die im Grunde ein einziges sind -- nur aus drei Blickwinkeln. \begin{defn}{Clique, Independent Set, Vertex Cover} Gegeben ein Graph $G$ und eine Zahl $k$. \begin{itemize} \item \problem{Clique}: eine Gruppe $C$, in der \emph{alle} paarweise verbunden sind; gibt es eine mit $|C| \ge k$? \item \problem{Independent Set (IS)}: eine Gruppe $I$, in der \emph{keine} zwei verbunden sind; gibt es eine mit $|I| \ge k$? \item \problem{Vertex Cover (VC)}: eine Knotenmenge $C$, die \emph{jede} Kante berührt; gibt es eine mit $|C| \le k$? \end{itemize} \end{defn} \begin{aha} \textbf{Das Dualitätsdreieck.} Diese drei sind dasselbe Problem in Verkleidung. In einem Graphen mit $n$ Knoten gilt: \begin{align*} C \text{ ist Clique in } G &\iff C \text{ ist Independent Set im Komplementgraphen } \bar G\\ &\iff V \setminus C \text{ ist Vertex Cover in } \bar G. \end{align*} Merksatz: \emph{Vertex Cover = alles außer einem Independent Set}; \emph{Clique = Independent Set, wenn man alle Kanten umdreht}. Verstehst du eines, verstehst du alle drei -- und die Reduktionen zwischen ihnen sind bloße Umformulierungen. \end{aha} \begin{bsp}{Das Dreieck an einem Mini-Graphen} Nimm ein Dreieck plus einen isolierten vierten Knoten: $V = \{1,2,3,4\}$, Kanten $\{1,2\},\{1,3\},\{2,3\}$. $\{1,2,3\}$ ist eine \emph{Clique} (alle verbunden). Im Komplement $\bar G$ (Kanten $\{1,4\},\{2,4\},\{3,4\}$) ist $\{1,2,3\}$ ein \emph{Independent Set} (keine zwei verbunden). Und $\{4\}$ ist dort ein \emph{Vertex Cover} -- der Knoten 4 berührt alle Kanten von $\bar G$. Ein Bild, drei Rollen. \end{bsp} \begin{defn}{Färbung und Hamiltonkreis} \problem{$k$-Color}: Kann man die Knoten mit $k$ Farben so färben, dass keine Kante zwei gleichfarbige Enden hat?\\ \problem{Hamiltonkreis (HK)}: Gibt es einen Rundweg, der \emph{jeden} Knoten genau einmal besucht? \end{defn} Diese beiden sind \glqq berühmte\grqq{} schwere Probleme. \problem{$k$-Color} erbt seine Schwere von \problem{3-SAT}, \problem{HK} von der 3-Literal-Variante $\problem{3-SAT}'$. \subsection{Eine Reduktion ganz durchgerechnet: $\problem{SAT} \redp \problem{$k$-Clique}$} Damit du \emph{siehst}, wie eine Reduktion konkret arbeitet, hier eine komplett. \begin{intuition} Idee: Baue für jedes Literal-Vorkommen einen Knoten. Verbinde zwei Knoten genau dann, wenn sie \emph{aus verschiedenen Klauseln} stammen und sich \emph{nicht widersprechen}. Eine erfüllende Belegung wählt aus jeder Klausel ein wahres Literal -- und diese Auswahl bildet dann eine Clique. \end{intuition} \begin{defn}{Die Konstruktion} Zur Formel $F = F_1 \wedge \dots \wedge F_m$ (Klausel $F_i$ mit Literalen $y_{i1},\dots$): \begin{itemize} \item \emph{Knoten:} $[i,j]$ für das $j$-te Literal in Klausel $i$. \item \emph{Kanten:} $\{[i,j],[i',j']\}$ genau dann, wenn $i \ne i'$ (verschiedene Klauseln) und die beiden Literale sich nicht widersprechen (nicht $x$ und $\neg x$). \item \emph{Gesuchte Cliquengröße:} $k = m$ (Anzahl der Klauseln). \end{itemize} \end{defn} \emph{Warum es stimmt.} Eine $m$-Clique muss aus jeder Klausel genau einen Knoten nehmen (Knoten derselben Klausel sind nie verbunden) und darf keine zwei widersprüchlichen Literale enthalten. Das ist \emph{genau} eine Belegung, die in jeder Klausel ein Literal wahr macht -- also eine erfüllende Belegung. Und umgekehrt. \begin{bsp}{Mit echten Zahlen} $F = (x_1 \vee x_2 \vee x_3) \wedge (\neg x_1 \vee \neg x_2) \wedge (x_1 \vee \neg x_2 \vee \neg x_3)$, also $m = 3$, gesucht $k = 3$. Es entstehen 8 Knoten (3 + 2 + 3). Kanten zwischen allen Paaren aus verschiedenen Klauseln \emph{außer} den widersprüchlichen, z.\,B. bekommt $\{[1,1],[2,1]\}$ ($x_1$ gegen $\neg x_1$) \emph{keine} Kante. Die Clique $\{[1,1],[2,2],[3,1]\}$ steht für $x_1,\ \neg x_2,\ x_1$ und liefert die Belegung $x_1 = \true$, $x_2 = \false$ (und $x_3$ frei). Tatsächlich erfüllt das $F$. \end{bsp} \subsection{Die Zahl- und Mengen-Probleme} \begin{defn}{3-DM, 3-EC, SubSet Sum, Partition, Knapsack} \begin{itemize} \item \problem{3-dim. Matching (3-DM)}: drei gleich große Mengen und Tripel; wähle Tripel, die jedes Element genau einmal treffen. \item \problem{3-Exact Cover (3-EC)}: 3-elementige Mengen; wähle einige, die das Universum \emph{exakt} (disjunkt) überdecken. \item \problem{SubSet Sum}: Zahlen $c_1,\dots,c_n$ und Ziel $K$; gibt es eine Teilmenge mit Summe genau $K$? \item \problem{Partition}: gibt es eine Teilmenge, die genau die \emph{Hälfte} der Gesamtsumme trägt? \item \problem{Knapsack}: Gegenstände mit Gewicht und Profit, Kapazität $B$, Zielprofit $P$; passt eine Auswahl mit Gewicht $\le B$ und Profit $\ge P$? \end{itemize} \end{defn} \begin{zushang} Diese fünf hängen in einer sauberen Kette: $\problem{SAT}\redp\problem{3-DM}\redp\problem{3-EC}\redp\problem{SubSet Sum} \redp\problem{Partition}$, und \problem{Knapsack} enthält \problem{SubSet Sum} als Spezialfall ($w_j = p_j$, $P = B$). Schwere fließt von der Logik (\problem{SAT}) über Mengen (\problem{3-EC}) bis zu reinen Zahlen (\problem{SubSet Sum}). \end{zushang} \subsection{Zwei kurze, elegante Reduktionen} \begin{bsp}{$\problem{3-EC} \redp \problem{SubSet Sum}$ -- Mengen werden Ziffern} Kodiere jede 3-elementige Menge als Bitvektor über dem Universum und lies ihn als Zahl zur \emph{Basis $n+1$}. Beispiel: $U = \{u_1,\dots,u_6\}$, Menge $\{u_1,u_5,u_6\}$ wird zum Bitvektor $100011$, also zur Zahl $(n{+}1)^0 + (n{+}1)^4 + (n{+}1)^5$. Zielwert $K$ ist die Zahl zum Vektor $111111$.\\ \emph{Der Trick:} Bei Basis $n+1$ und höchstens $n$ Summanden gibt es \emph{keinen Übertrag}. Eine Teilmenge trifft die Zielsumme genau dann, wenn jede Stelle exakt einmal getroffen wird -- also eine exakte Überdeckung. \end{bsp} \begin{bsp}{$\problem{SubSet Sum} \redp \problem{Partition}$ -- zwei Zusatzzahlen} Aus $(c_1,\dots,c_n,K)$ mit $N = \sum_j c_j + 1$ mache die Zahlenmenge, ergänzt um $c_{n+1} = N-K$ und $c_{n+2} = K+1$. Die Gesamtsumme ist dann $2N$, die Hälfte $N$.\\ \emph{Der Trick:} Die zwei Zusatzzahlen summieren sich zu $N+1$ -- sie können also nie in derselben Hälfte landen. Eine Halbierung existiert genau dann, wenn eine Original-Teilmenge den Wert $K$ trifft. \end{bsp} \begin{defn}{Scheduling: $P\|\Cmax$} $n$ Jobs mit Laufzeiten $p_1,\dots,p_n$, $m$ identische Maschinen. Verteile die Jobs so, dass die am stärksten belastete Maschine -- der \emph{Makespan} $\Cmax = \max_i \sum_{J_j \text{ auf } M_i} p_j$ -- minimal wird. \end{defn} \begin{zushang} $P\|\Cmax$ ist schon für $m = 2$ Maschinen NP-vollständig -- über $\problem{Partition} \redp P2\|\Cmax$: Zwei Maschinen exakt gleich auszulasten, heißt die Jobs zu \emph{halbieren}. Damit schließt sich der Kreis von der Logik bis zum Scheduling. \end{zushang} \begin{selbstcheck} Warum ist \problem{SubSet Sum} \glqq schwer\grqq, obwohl es doch nur um Addieren von Zahlen geht?\\[0.3em] \emph{Antwort:} Weil die Zahlen \emph{binär} kodiert sind (Stolperstein aus Kapitel 2). Ihr Wert ist exponentiell in der Eingabelänge. Alle Teilsummen auszuprobieren bedeutet $2^n$ Teilmengen -- das simple \glqq Addieren\grqq{} versteckt eine exponentielle Suche. \end{selbstcheck} % ################################################################## \section{Wie schwer \emph{genau}? Die ETH} % ################################################################## \begin{ziel} NP-Vollständigkeit sagt nur \glqq vermutlich nicht polynomiell\grqq. Aber \emph{wie} exponentiell? Die Exponentialzeit-Hypothese (ETH) gibt eine schärfere Antwort -- und erlaubt konkrete untere Laufzeitschranken. \end{ziel} \subsection{Die Lücke, die NP-Vollständigkeit lässt} NP-Vollständigkeit ist ein grobes Sieb. Sie unterscheidet nicht zwischen einem Problem, das $2^n$ braucht, und einem, das nur $2^{\sqrt n}$ braucht -- beide sind \glqq nicht polynomiell\grqq. Für viele Fragen will man aber genau wissen: \emph{Geht es wenigstens subexponentiell?} \begin{defn}{Klein-o und \glqq subexponentiell\grqq} $f(n) = o(g(n))$ heißt: $f$ wächst \emph{echt langsamer} als $g$, also $f(n)/g(n) \to 0$. Wichtig: $\delta n$ ist \emph{nicht} $o(n)$ für festes $\delta > 0$. Ein \glqq $2^{o(n)}$-Algorithmus\grqq{} ist einer, dessen Exponent langsamer als linear wächst -- er läuft \emph{subexponentiell} (z.\,B. $2^{\sqrt n}$). \end{defn} \subsection{Die Hypothese und warum man sie braucht} \begin{defn}{Exponentialzeit-Hypothese (ETH)} Es gibt eine Konstante $\delta > 0$, sodass \problem{3-SAT} mit $n$ Variablen \emph{nicht} in Zeit $2^{\delta n}\cdot\poly$ gelöst werden kann. Kurz: es gibt \emph{keinen} $2^{o(n)}$-Algorithmus für \problem{3-SAT}. \end{defn} Das ist eine \emph{Annahme}, stärker als $\Pclass \ne \NP$, aber allgemein geglaubt (die besten bekannten 3-SAT-Algorithmen brauchen $c^n$). Aus ihr leitet man untere Schranken für viele Probleme ab. \begin{intuition} Das Beweismuster ist immer \emph{Kontraposition über eine Reduktion}: \glqq Gäbe es einen zu schnellen Algorithmus für mein Zielproblem, dann ergäbe die Reduktion einen zu schnellen Algorithmus für 3-SAT -- Widerspruch zur ETH.\grqq{} Man überträgt also die Härte-Annahme entlang eines Pfeils, genau wie bei der NP-Vollständigkeit -- nur zählt man diesmal die \emph{Größe} der konstruierten Instanz mit. \end{intuition} \begin{satz}{Sparsification-Lemma (und warum es nötig ist)} Unter der ETH gibt es sogar keine $2^{o(m)}$-Lösung für \problem{3-SAT}, wobei $m$ die \emph{Klauselzahl} ist.\\ \emph{Warum man das braucht:} Die ETH spricht über die Variablenzahl $n$. Viele Reduktionen erzeugen ihre Instanzgröße aber aus der Klauselzahl $m$. Weil $m$ gegenüber $n$ groß sein kann, folgt eine $m$-Schranke \emph{nicht} direkt aus der ETH. Das Sparsification-Lemma schließt genau diese Lücke. \end{satz} \begin{aha} Faustregel für die Praxis: \emph{Hängt der Parameter deiner konstruierten Instanz an der Klauselzahl $m$, zitiere das Sparsification-Lemma.} Das ist der Standardschritt in jedem ETH-Beweis -- und der, den man am leichtesten vergisst. \end{aha} Unter der ETH bekommt man so untere Schranken $2^{o(n)}$ z.\,B. für \problem{3-Color}, \problem{Clique}, \problem{Vertex Cover}, \problem{Independent Set} sowie \problem{SubSet Sum} und \problem{Partition}. \begin{selbstcheck} Wenn die ETH \emph{falsch} ist -- folgt dann $\Pclass = \NP$?\\[0.3em] \emph{Antwort:} Nein. \glqq ETH falsch\grqq{} heißt nur: 3-SAT geht in $2^{o(n)}$ -- das kann immer noch superpolynomiell sein, z.\,B. $2^{\sqrt n}$. Umgekehrt gilt aber: $\Pclass = \NP$ würde die ETH sofort widerlegen. \end{selbstcheck} % ################################################################## \section{Damit leben: gute Näherungen}\label{sec:approx} % ################################################################## \begin{ziel} Wenn ein Problem (vermutlich) keine schnelle \emph{exakte} Lösung hat, geben wir uns mit einer \emph{beweisbar guten} Näherung zufrieden. Wir lernen, was \glqq beweisbar gut\grqq{} heißt, und sehen die wichtigsten Näherungsalgorithmen der Vorlesung in Aktion. \end{ziel} \subsection{Was heißt \glqq gute Näherung\grqq?} \begin{defn}{Multiplikative Güte} Sei $\OPT(I)$ der optimale Wert einer Instanz $I$. Ein Algorithmus $A$ hat \emph{Güte $\alpha$}, wenn für \emph{alle} Instanzen gilt: \begin{itemize} \item Minimierung (z.\,B. TSP, Scheduling): $A(I) \le \alpha\cdot\OPT(I)$ -- \glqq höchstens $\alpha$-mal so groß wie das Optimum\grqq. \item Maximierung (z.\,B. Knapsack): $\OPT(I) \le \alpha\cdot A(I)$ -- \glqq mindestens ein $\alpha$-tel des Optimums\grqq. \end{itemize} Die Güte ist \emph{scharf}, wenn es Instanzen gibt, die den Faktor (fast) erreichen. \end{defn} \begin{intuition} Güte $\alpha$ ist eine \emph{Garantie für den schlimmsten Fall}. Güte 2 bei einem Minimierungsproblem heißt: Egal welche Eingabe -- meine Lösung ist nie mehr als doppelt so teuer wie die beste mögliche. Kleineres $\alpha$ ist besser; $\alpha = 1$ wäre exakt optimal. \end{intuition} \begin{defn}{PTAS, EPTAS, FPTAS -- Näherung nach Wunsch} Manche Probleme erlauben eine \emph{ganze Familie} $(A_\varepsilon)$ mit Güte $1+\varepsilon$ für \emph{jedes} $\varepsilon > 0$ -- man stellt die Genauigkeit selbst ein. Nach Laufzeit gestaffelt: \begin{itemize} \item \emph{PTAS}: für jedes feste $\varepsilon$ polynomiell in $n$ (aber $\varepsilon$ darf im Exponenten stecken, z.\,B. $n^{1/\varepsilon}$). \item \emph{EPTAS}: Laufzeit $f(1/\varepsilon)\cdot\poly(n)$ -- $\varepsilon$ raus aus dem Exponenten von $n$. \item \emph{FPTAS}: polynomiell in $n$ \emph{und} $1/\varepsilon$ (z.\,B. $O(n^3/\varepsilon)$). Die stärkste Form. \end{itemize} \emph{Pseudopolynomiell} nennt man eine Laufzeit, die polynomiell in den \emph{Zahlenwerten} der Eingabe ist -- erinnere den Stolperstein: das ist \emph{nicht} polynomiell in der Eingabelänge. \end{defn} \subsection{TSP: von \glqq unmöglich\grqq{} zu Güte $1{,}5$} Das Traveling-Salesman-Problem (kürzeste Rundreise durch alle Städte) zeigt die ganze Spannweite der Approximation. \begin{satz}{Allgemeines TSP ist gar nicht approximierbar} Für beliebige Distanzen gibt es \emph{keinen} Näherungsalgorithmus mit beschränkter Güte -- außer $\Pclass = \NP$.\\ \emph{Beweisidee:} Reduziere \problem{Hamiltonkreis}. Echte Kanten bekommen Distanz 1, fehlende Kanten eine \emph{riesige} Distanz. Ein Algorithmus mit beschränkter Güte müsste die billige (Hamilton-)Tour von der teuren unterscheiden -- und könnte damit \problem{HK} exakt lösen. \end{satz} Der Ausweg ist eine sinnvolle Zusatzannahme: das \emph{metrische} TSP. Distanzen sind symmetrisch und erfüllen die \emph{Dreiecksungleichung} $d(i,j) \le d(i,k) + d(k,j)$ -- ein Umweg ist nie kürzer als der direkte Weg. Das ist realistisch (echte Entfernungen) und macht das Problem approximierbar. \begin{defn}{Eulerkreis} Ein \emph{Eulerkreis} in einem (Multi-)Graphen ist ein Rundweg, der jede \emph{Kante} genau einmal benutzt. Er existiert genau dann, wenn der Graph zusammenhängend ist und \emph{jeder Knoten geraden Grad} hat. \end{defn} \begin{intuition} Beide TSP-Algorithmen folgen demselben Dreisprung: (1) baue ein billiges Gerüst, das alle Städte verbindet (einen minimalen Spannbaum), (2) mache daraus einen Eulerkreis (alle Grade gerade), (3) kürze ihn zu einer Tour ab -- was dank Dreiecksungleichung nie teurer wird. \end{intuition} \begin{defn}{$\Delta$TSP$_1$ -- MST-Verdopplung (Güte 2)} \begin{enumerate} \item Minimalen Spannbaum $T$ berechnen. \item Jede Kante von $T$ verdoppeln $\to$ alle Grade gerade. \item Eulerkreis bestimmen. \item Zur Tour abkürzen (schon besuchte Städte überspringen). \end{enumerate} \emph{Warum Güte 2:} $w(T) \le \OPT$ (eine optimale Tour minus eine Kante ist ein Spannbaum), Verdoppeln gibt $2w(T)$, Abkürzen verlängert nicht. Also $\le 2\,\OPT$. \end{defn} \begin{bsp}{$\Delta$TSP$_1$ komplett durchgerechnet} Städte $\{A,B,C,D,E\}$ mit u.\,a. $d(A,E)=1$, $d(B,C)=1$, $d(A,C)=2$, $d(C,D)=2$ (die übrigen 2 oder 3). Optimale Tour: $[C,B,D,E,A,C]$ mit Länge $\mathbf{8}$. \begin{itemize} \item \emph{MST} $T$: Kanten $A$--$E\,(1)$, $B$--$C\,(1)$, $A$--$C\,(2)$, $C$--$D\,(2)$; Gewicht $w(T)=6$. \item \emph{Verdoppeln} $\to$ Multigraph mit Gewicht $12$. \item \emph{Eulerkreis} $[C,A,E,A,C,B,C,D,C]$, Länge $12$. \item \emph{Abkürzen} $\to$ Tour $[C,A,E,B,D,C]$ mit Länge $\mathbf{10}$ $\le 2\cdot 8$. \end{itemize} \end{bsp} Christofides verbessert Schritt 2: Statt \emph{alle} Kanten zu verdoppeln, repariert er nur die \glqq schiefen\grqq{} Knoten -- die mit ungeradem Grad. \begin{defn}{$\Delta$TSP$_2$ -- Christofides (Güte $1{,}5$)} \begin{enumerate} \item Minimalen Spannbaum $T$ berechnen. \item $X :=$ Knoten mit \emph{ungeradem} Grad in $T$ (ihre Anzahl ist gerade). \item Minimales perfektes Matching $K$ auf $X$ berechnen. \item $T + K$ hat überall geraden Grad $\to$ Eulerkreis $\to$ abkürzen. \end{enumerate} \emph{Warum Güte $1{,}5$:} Das Matching kostet höchstens $\OPT/2$ (die optimale Tour zerfällt auf $X$ in zwei Matchings), also $\le w(T) + \OPT/2 \le 1{,}5\,\OPT$. \end{defn} \begin{bsp}{Christofides am selben Graphen} MST wie oben. Ungerade Grade: $X = \{B,C,D,E\}$. Matching-Kosten: $d(B,C)=1,\ d(D,E)=2,\ d(B,E)=2,\ d(C,D)=2,\ d(B,D)=3,\ d(C,E)=3$. Minimales perfektes Matching: $\{B\text{--}C,\ D\text{--}E\}$ mit Gewicht $3$. Der Eulerkreis $[C,B,C,A,E,D,C]$ kürzt ab zu $[C,B,A,E,D,C]$ mit Länge $\mathbf{9}$ -- besser als die $10$ von $\Delta$TSP$_1$. \end{bsp} \begin{stolper} Zwei Details, die Christofides oft falsch gemacht wird: (1) Das Matching wird \emph{nur} auf den ungerad-gradigen Knoten des MST gebildet, nicht auf allen. (2) Ohne die Dreiecksungleichung bricht das Abkürzen zusammen -- nur sie garantiert, dass die abgekürzte Tour nicht länger wird. \end{stolper} \subsection{Knapsack: warum Gier allein scheitert} Der Rucksack als Optimierungsproblem: pack Gegenstände mit maximalem Gesamtprofit ein, ohne die Kapazität $B$ zu sprengen. \begin{intuition} Der naheliegende \emph{Greedy}: nach \glqq Profit pro Gewicht\grqq{} sortieren und der Reihe nach einpacken, was passt. Meistens gut -- aber ohne jede Garantie. \end{intuition} \begin{bsp}{Greedy kann beliebig schlecht sein} Zwei Gegenstände: $(w_0,p_0) = (1,1)$ und $(w_1,p_1) = (B, B-1)$, Kapazität $B$. Greedy nimmt Gegenstand 0 (Dichte 1 schlägt $(B-1)/B$), Gewinn nur $1$. Optimal wäre Gegenstand 1 mit Gewinn $B-1$. Das Verhältnis $\OPT/\mathrm{GA} = B-1$ wächst unbeschränkt -- \emph{keine} konstante Güte. \end{bsp} \begin{aha} Die Reparatur ist verblüffend einfach. \emph{Modified Greedy (MGA):} rechne Greedy \emph{und} \glqq nimm nur den einen profitabelsten Gegenstand\grqq, gib das Bessere aus. Schon das garantiert Güte 2. Der Grund: Greedy verliert nur am einen \glqq Split-Item\grqq, das nicht mehr passte -- und dessen Profit fängt das Einzel-Item ab. \end{aha} Will man noch näher ans Optimum, gibt es zwei Stufen: der \emph{Sahni}-Algorithmus probiert alle kleinen Vorauswahlen (Güte $1 + 1/k$, ein PTAS), und das \emph{FPTAS} skaliert die Profite herunter und löst exakt per dynamischer Programmierung -- Güte $1+\varepsilon$ in Zeit $O(n^3/\varepsilon)$. \subsection{Scheduling: einfache Regeln, scharfe Schranken} Zurück zu $P\|\Cmax$: $n$ Jobs auf $m$ Maschinen, minimiere die höchste Last. \begin{defn}{List Scheduling und LPT} \emph{List Scheduling:} geh die Jobs der Reihe nach durch, leg jeden auf die \emph{momentan am wenigsten belastete} Maschine.\\ \emph{LPT (Longest Processing Time):} sortiere die Jobs zuerst \emph{absteigend}, dann List Scheduling. \end{defn} \begin{satz}{Güten von List Scheduling und LPT} List Scheduling hat Güte $2 - \frac1m$, LPT die bessere Güte $\frac43 - \frac1{3m}$ -- beide scharf.\\ \emph{Beweisidee (List Scheduling):} Sei $J_k$ der letzte Job auf der vollsten Maschine. Vor seiner Zuweisung war diese Maschine die leerste, also waren \emph{alle} mindestens so voll. Mit den zwei Universalschranken $\OPT \ge \frac1m\sum p_i$ (Durchschnittslast) und $\OPT \ge p_{\max}$ (größter Job) folgt die Schranke. \end{satz} \begin{intuition} Diese \emph{zwei Schranken} -- Durchschnittslast und größter Job -- sind das Universalwerkzeug \emph{aller} Scheduling-Güte-Beweise. Sortieren (LPT) hilft, weil der störende \glqq letzte große Job\grqq{} dann früh drankommt, wenn noch alles leer ist. \end{intuition} \begin{bsp}{Warum List Scheduling die Schranke wirklich erreicht} $m(m-1)$ Jobs der Größe 1, danach \emph{ein} Job der Größe $m$ -- in dieser Reihenfolge. List Scheduling verteilt die Einsen gleichmäßig (je $m-1$) und setzt den großen obendrauf: Last $2m-1$. Optimal wäre: großer Job allein, Einsen auf die restlichen Maschinen -- Last $m$. Verhältnis $\frac{2m-1}{m} = 2 - \frac1m$. LPT würde den großen Job zuerst legen und das vermeiden. \end{bsp} \subsection{MAX-3-SAT: Güte 2 fast geschenkt}\label{sec:max3sat} \begin{bsp}{Zwei Belegungen genügen} Maximiere die Zahl erfüllter Klauseln. Werte die Formel nur zweimal aus: einmal \glqq alles falsch\grqq{} ($\beta_0$), einmal \glqq alles wahr\grqq{} ($\beta_1$), nimm das Bessere. Jede Klausel hat ein positives \emph{oder} ein negatives Literal, wird also von $\beta_0$ \emph{oder} $\beta_1$ erfüllt. Damit erfüllen beide zusammen $\ge m$ Klauseln, die bessere also $\ge m/2 \ge \OPT/2$. Güte 2 mit zwei Zeilen Aufwand. \end{bsp} \begin{selbstcheck} Warum braucht Christofides zwingend die Dreiecksungleichung, $\Delta$TSP$_1$ scheinbar auch, das allgemeine TSP aber \glqq gibt es gar nicht\grqq?\\[0.3em] \emph{Antwort:} Beide Näherungsalgorithmen \emph{kürzen} einen Eulerkreis ab -- das darf nur nicht verteuern, was allein die Dreiecksungleichung sichert. Ohne sie (allgemeines TSP) kann Abkürzen beliebig teuer werden, und tatsächlich ist dort \emph{jede} beschränkte Güte unmöglich (außer $\Pclass = \NP$). \end{selbstcheck} % ################################################################## \section{Jenseits von NP: das Halteproblem}\label{sec:halt} % ################################################################## \begin{ziel} Ein kurzer Blick über den Rand: ein Problem, das NP-schwer ist -- aber \emph{gar nicht} in $\NP$ liegt, weil es überhaupt nicht lösbar ist. Das zeigt, dass \glqq schwer\grqq{} und \glqq in NP\grqq{} wirklich zwei verschiedene Dinge sind. \end{ziel} \begin{defn}{Halteproblem} Gegeben die Beschreibung eines Programms $M$ und einer Eingabe $w$: \emph{Hält $M$ auf $w$ irgendwann an, oder läuft es ewig?} \end{defn} Das Halteproblem ist \emph{unentscheidbar} -- kein Algorithmus löst es, mit keiner Laufzeit. Trotzdem ist es NP-schwer. \begin{aha} Man reduziert \problem{SAT} darauf: Baue zu einer Formel $\varphi$ ein Programm $M_\varphi$, das \emph{alle} Belegungen durchprobiert und genau dann hält, wenn eine erfüllende existiert. Dann gilt: $\varphi$ erfüllbar $\iff$ $M_\varphi$ hält. Der Clou: $M_\varphi$ läuft womöglich ewig -- aber die \emph{Konstruktion} von $M_\varphi$ aus $\varphi$ ist billig, und nur darauf kommt es bei einer Reduktion an. Also ist das Halteproblem mindestens so schwer wie \problem{SAT}, aber es liegt nicht in $\NP$ (nicht einmal entscheidbar). NP-schwer $\ne$ NP-vollständig. \end{aha} % ################################################################## \section{Das große Ganze} % ################################################################## \begin{ziel} Wir ziehen die Fäden zusammen. Eine Landkarte, ein Selbsttest -- und der Weg nach vorn. \end{ziel} \subsection{Die Reise in einem Bild} \begin{center} \small \begin{tabular}{p{3.4cm}p{10.4cm}} \toprule Station & Kernidee \\ \midrule $\Pclass$ & effizient \emph{lösbar} (polynomiell)\\ $\NP$ & effizient \emph{überprüfbar} (Zertifikat prüfen / raten)\\ $\Pclass \subseteq \NP$ & Lösen ist schwerer (oder gleich schwer) wie Prüfen; Gleichheit offen\\ Reduktion $A\redp B$ & \glqq $B$ mindestens so schwer wie $A$\grqq; Richtung: bekannt $\redp$ neu\\ NP-vollständig & die schwersten in $\NP$; \problem{SAT} ist der Anker (Cook--Levin)\\ Vererbungskorollar & neues Problem schwer zeigen: eine Reduktion + $\in\NP$\\ ETH & schärfer als NP-Vollständigkeit: konkrete $2^{o(\cdot)}$-Schranken\\ Approximation & bei schweren Optimierungsproblemen: beweisbar gute Näherung\\ \bottomrule \end{tabular} \end{center} \subsection{Verständnis-Check: wahr oder falsch?} Kannst du jede Aussage begründen? Die Begründung zählt, nicht das Kreuz. \begin{center} \small \begin{tabular}{p{7.4cm}cp{4.7cm}} \toprule Aussage & W/F & Begründung \\ \midrule Löst eine ratende Maschine ein Problem in Polyzeit, dann auch eine gewöhnliche. & F$^{*}$ & Das wäre $\Pclass = \NP$ -- unbekannt. \\ \addlinespace $A$ NP-schwer $\Rightarrow A \in \NP$. & F & Halteproblem: NP-schwer, aber nicht einmal lösbar. \\ \addlinespace $L \in \NP$ und $L \redp \problem{3-SAT}$ $\Rightarrow$ $L$ NP-vollständig. & F & Falsche Richtung: \emph{auf} 3-SAT reduzieren zeigt keine Schwere. \\ \addlinespace $\problem{3-SAT}\redp L$ und $L \redp \problem{3-SAT}$ $\Rightarrow$ $L$ NP-vollständig. & W & Erstes gibt Schwere, zweites gibt $L\in\NP$. \\ \addlinespace $\problem{3-SAT}\in\Pclass$, aber $\problem{Clique}\notin\Pclass$ ist möglich. & F & $\problem{Clique}\redp\problem{3-SAT}$; dann wäre auch Clique in $\Pclass$. \\ \addlinespace ETH falsch $\Rightarrow \Pclass = \NP$. & F & $2^{o(n)}$ kann trotzdem superpolynomiell sein. \\ \bottomrule \end{tabular} \end{center} {\footnotesize $^{*}$ nicht als wahr beweisbar; äquivalent zu $\Pclass = \NP$.} \subsection{Wie es weitergeht} \begin{aha} Du hast jetzt das \emph{Warum} beisammen: Was Probleme schwer macht, wie man Schwere von einem Problem auf ein anderes überträgt, wo die Grenzen liegen und was man tut, wenn exakte Lösungen zu teuer sind. Das ist das Fundament. \end{aha} \noindent Der nächste Schritt ist die \emph{Praxis}. Nimm dir die Präsenz-, Haus- und Klausuraufgaben vor und führe dort selbst aus, was hier nur als Idee stand: Reduktionen vollständig beweisen (beide Richtungen!), Güte-Schranken sauber herleiten, Worst-Case-Instanzen konstruieren. Dieser Guide gibt dir das Verständnis -- die Aufgaben geben dir das Können. \begin{center} \itshape Viel Erfolg. \end{center} \end{document}