--- title: Find an Eulerian Path with the Hierholzer Algorithm date: 2024-03-13 pseudocode: true slug: hierholzer-algorithm draft: true --- An Eulerian path of a graph is a path that passes once on every edge of the graph. The Hierholzer algorithm allows to find this path. The algorithm proceeds as follows: 1. Choose any vertex $v_0$ of the graph $G = (V, E)$. Starting from $v_0$, build a path $c$ that passes only once per edge until it reaches $v_0$ again. 2. If $c$ is an Eulerian cycle, we have found the Eulerian path, else - Ignore all edges from $c$. - For the first vertex $u$ from $c$ whose degree is not null, build an other cycle $c'$ that passes only once per edges, and does not pass in the previously visited edges. - Insert $c'$ in $c$ by replacing the starting node $u$. - Repeat the second step until we have an Eulerian path. ## Pseudocode
\begin{algorithm}
\caption{Hierholzer algorithm for Eulerian path finding}
\begin{algorithmic}
\Function{EulerianPath}{$G: (V, E)$}
\State $c \gets$ an empty Doubly Linked List
\State $E' \gets E$
\State $v_0$ becomes the first vertex from $V$
\State $u \gets v_0$
\State \Comment{Find the first cycle}
\While{$\exists (u, v) \in E'$}
\State $c$.insert($u$)
\State $u \gets v$
\State $E' \gets E' \setminus \{(u, v)\}$
\If {$u = v_0$}
\Break
\EndIf
\EndWhile
\State \Comment{Add the other cycles}
\While {$c$.length $< |E|$}
\State \Comment{Find the next vertex with non null degree}
\State $v_0 \gets c$.value
\While {$\nexists (v_0, v) \in E'$}
\State $c \gets c$.next
\State $v_0 \gets c$.value
\State $u \gets v_0$
\EndWhile
\State \Comment{Insert the next cycle in $c$}
\State $c$.delete() \Comment{Ensure $v_0$ is not present twice there}
\While {$\exists (u, v) \in E'$}
\State $c$.insert($u$)
\State $u \gets v$
\State $E' \gets E' \setminus \{(u, v)\}$
\If {$u = v_0$}
\Break
\EndIf
\EndWhile
\EndWhile
\EndFunction
\end{algorithmic}
\end{algorithm}
## Rust implantation
```rust
use std::collections::{HashMap, LinkedList};
use std::io::Error;
/// Eulerian path
///
/// Warning: this assumes the graph is Eulerian
fn eulerian_path(graph: HashMap