Euler Tour Tree
An Euler tour tree is a dynamic forest data structure introduced by Monika R. Henzinger and Valerie King in 1995 that represents unrooted trees as balanced binary search trees over their directed Euler tour sequences, supporting edge insertions, edge deletions, rerooting, and subtree aggregate queries in O(log n) time.
Euler tour tree (ETT) is a dynamic graph data structure within computation and algorithms introduced by Monika R. Henzinger and Valerie King in 1995 (building on Robert E. Tarjan and Uzi Vishkin's 1984 parallel Euler tour technique) to maintain a dynamic forest of unrooted trees under edge insertions (link), edge deletions (cut), tree rerooting, connected-component queries, and subtree aggregate queries in O(log n) time per operation. Whereas Daniel Sleator and Robert E. Tarjan's 1983 link-cut tree decomposes a tree into vertex-disjoint preferred paths and excels at aggregating weights along a root-to-vertex path, an Euler tour tree linearizes the entire two-dimensional topology of each tree into a single one-dimensional sequence by recording its depth-first Euler tour, and stores that sequence inside a self-balancing binary search tree such as a red-black tree, AVL tree, treap, or splay tree.
Because every subtree of a rooted tree corresponds to a single contiguous interval of the Euler tour sequence, while inserting or deleting a tree edge splices or excises at most two contiguous intervals of the tour, all topological updates and whole-subtree associative aggregations reduce directly to O(log n) sequence split and join (concatenation) operations. In computational complexity theory and algorithm engineering, Euler tour trees serve as the backbone of randomized and deterministic dynamic connectivity algorithms (including the Holm-de Lichtenberg-Thorup O(log2 n) polylogarithmic dynamic graph connectivity structure) and dynamic minimum spanning tree maintenance.
Linearizing a Tree via Directed Euler Tours
Let T = (V, E) be an unrooted tree on n = |V| vertices and n โ 1 undirected edges. To linearize T into a cycle, replace each undirected edge {u, v} โ E with two oppositely directed arcs (u, v) and (v, u). In the resulting directed multigraph D(T), every vertex v โ V has in-degree equal to out-degree (degโ(v) = deg+(v) = deg(v)), so D(T) is Eulerian and admits a directed Euler tour that traverses every directed arc (u, v) once before returning to the starting vertex r.
Two closely related linear encodings of the Euler tour are used in practice:
- Vertex-Visit Sequence (2n โ 1 Entries): Starting a depth-first traversal at root r, record each vertex every time the walk visits it (upon initial entry and upon returning from each child subtree). Because the walk starts at r and takes 2(n โ 1) directed steps, the vertex-visit sequence ET(T) has length 2n โ 1, in which each vertex v appears deg(v) times (except the root r, which appears deg(r) + 1 times).
- Directed-Arc Sequence (2n โ 2 Arcs + n Self-Loops): Alternatively, store only the 2n โ 2 directed arcs (u, v) in their Euler traversal order, augmented by a canonical self-loop arc (v, v) at the first visit to each vertex v โ V so that vertex weights and isolated single-vertex trees (n = 1, 0 edges) have a dedicated node of length 3n โ 2.
To distinguish the single canonical representative of a vertex v from its secondary revisit appearances when computing subtree sums or sizes, only the first occurrence first(v) (or the self-loop node (v, v)) holds the active vertex weight w(v), while all secondary occurrences of v store the monoid identity element 0. Each vertex v maintains direct pointers to its first and last occurrences (first(v) and last(v)), and each undirected edge e = {u, v} maintains direct pointers to the two tree nodes representing its directed arcs (u, v) and (v, u).
Implementing Topological Operations via Balanced BST Splits and Joins
Each tree's Euler tour sequence is stored as the in-order traversal of a balanced binary search tree (such as a weight-balanced treap, splay tree, red-black tree, or 2โ3 finger tree) equipped with parent pointers, where keys are implicit sequence positions rather than explicit numbers. The balanced BST supports two fundamental primitives in O(log n) time:
- Split(S, x): Partitions the sequence S at node x into (Sleft, Sright), where Sleft contains all elements preceding x and Sright begins with x.
- Join(S1, S2): Concatenates two sequences S1 and S2 into a single balanced BST S1 ยท S2.
Using only Split, Join, and upward root traversal, an Euler tour tree implements all dynamic forest primitives in O(log n) time:
1. Connected-Component Queries: FindRoot(v) and Connected(u, v)
To determine whether two vertices u and v belong to the same connected component of the forest, start at node first(u) and node first(v) in the balanced BST and follow parent pointers up to their respective BST roots in O(log n) time. Because each connected component is represented by a single BST, u and v are connected in the forest if and only if their BST roots are identical. Unlike a disjoint-set data structure, which achieves O(ฮฑ(n)) amortized time for insertion-only connectivity, the Euler tour tree maintains full connectivity under arbitrary interleaved edge deletions.
2. Rerooting a Tree: Reroot(T, r)
Changing the designated root of tree T from its current root r0 to a new vertex r corresponds to a cyclic shift of the Euler tour cycle so that the tour begins and ends at r. In the vertex-visit representation (where the trailing duplicate of r0 is dropped when viewing the tour as a circular cycle of 2n โ 2 steps), splitting the sequence just before first(r) into (A, B), swapping the two halves into B ยท A, and appending a new closing visit to r executes via two Split and two Join calls in O(log n) time.
3. Deleting an Edge: Cut(u, v)
When an undirected edge e = {u, v} (with u closer to the root than v) is deleted, the directed arc (u, v) marks the entry into v's subtree Tv, and the reverse directed arc (v, u) marks the exit from Tv back to u. Consequently, the original Euler tour S decomposes into three contiguous segments positioned around the two arcs (u, v) and (v, u):
S = J ยท [(u, v)] ยท K ยท [(v, u)] ยท L,
where the middle segment K is the complete, self-contained Euler tour of the child subtree Tv, and the outer concatenation J ยท L (merging the two occurrences of u on either side of the excised excursion) is the valid Euler tour of the remaining tree T \ Tv. Performing two Split operations at (u, v) and (v, u) to excise K and one Join operation to weld J and L back together completes Cut(u, v) in O(log n) time.
4. Inserting an Edge: Link(u, v)
To add an undirected edge e = {u, v} connecting two vertices u and v in distinct trees Tu and Tv (verified first via Connected(u, v) = false), first execute Reroot(Tv, v) so that the Euler tour K of Tv starts and ends at v. Next, split the Euler tour of Tu right after an occurrence of u into (J, L), and join the pieces with the two newly allocated directed arcs (u, v) and (v, u):
Snew = J ยท [(u, v)] ยท K ยท [(v, u)] ยท L.
This requires one reroot, one Split, and three Join calls, running in O(log n) time.
| Dynamic Tree / Connectivity Structure | Link / Cut Time | Path Aggregate (u to v) | Subtree Aggregate (Tv) | Non-Tree Edges (General Graphs) | Space Overhead |
|---|---|---|---|---|---|
| Disjoint-Set Data Structure (Union-Find) | O(ฮฑ(n)) link only (no cut) | Not supported | Component size in O(ฮฑ(n)) | Incremental connectivity | O(n) words |
| Euler Tour Tree (Henzinger & King) | O(log n) | Not native (requires ยฑ1 cancelling) | O(log n) associative monoid | Via HDT level hierarchy (O(log2 n)) | O(n) nodes (3n โ 2) |
| Link-Cut Tree (Sleator & Tarjan) | O(log n) amortized | O(log n) native | Invertible groups or virtual-child BSTs | Via ST-tree / MST replacement | O(n) nodes |
| Top Tree (Alstrup et al.) | O(log n) | O(log n) native | O(log n) native | Via cluster contraction | O(n) clusters |
| b-ary Euler Tour Tree (B-Tree) | O(log n / log log n) | Not native | O(log n / log log n) | Dynamic connectivity in O(log2 n / log log n) | O(n) words |
Subtree Aggregate Queries vs. Link-Cut Trees
The primary algorithmic advantage of an Euler tour tree over a standard link-cut tree is its native support for non-invertible subtree aggregations (such as computing the minimum or maximum vertex weight in a subtree Tv, or applying a lazy range addition to all vertices in Tv, analogous to a segment tree or Fenwick tree).
In a link-cut tree, a vertex v can have arbitrarily many "light" (dashed) children whose subtrees are not part of v's preferred splay path; maintaining the minimum over all light children requires either an invertible operation (such as addition, where subtracting a detached child's sum takes O(1) time) or storing an auxiliary balanced heap at every vertex. In an Euler tour tree, by contrast, the entire subtree Tv rooted at v (when u is v's parent) is precisely the contiguous subsegment K bounded between the directed arc (u, v) and the reverse arc (v, u). Consequently, augmenting each BST node with the associative monoid aggregate of its BST subtreeโexactly as in a segment treeโallows querying the sum, minimum, maximum, or count of any subtree Tv (or applying a lazy tag to Tv) by temporarily splitting out K (or querying the interval between (u, v) and (v, u)) in O(log n) time.
Applications in Fully Dynamic Graph Connectivity
In Monika Henzinger and Valerie King's 1995 randomized dynamic connectivity algorithm and Jacob Holm, Kristian de Lichtenberg, and Mikkel Thorup's 2001 deterministic O(log2 n) amortized dynamic connectivity structure (the HDT algorithm), a general undirected graph G = (V, E) undergoing arbitrary edge insertions and deletions is maintained via a hierarchy of โlog2 nโ + 1 spanning forests F0 โ F1 โ ... โ FL, where each forest Fi is represented as an Euler tour tree:
- Every tree edge e and non-tree edge has a level โ(e) โ [0, L] satisfying the invariant that any connected component at level i has at most โn / 2iโ vertices.
- When a spanning-tree edge e = {u, v} is deleted, Cut(u, v) splits its component into Tu and Tv across levels 0 through โ(e). To determine whether G remains connected, the algorithm must locate a replacement non-tree edge joining Tu and Tv.
- Because each Euler tour tree node is augmented with the count of incident level-i non-tree edges in its subtree (a subtree aggregate), the HDT algorithm identifies the smaller subtree (say |Tu| โค |Tv|), traverses only the BST subtrees of Tu that have a non-zero count of incident level-i edges in O(log n) time per candidate edge, promotes inspected non-tree edges that fail to cross the cut to level i + 1 (at most log2 n promotions per edge over its lifetime), and reconnects the Euler tour trees in O(log2 n) amortized time.
Frequently Asked Questions
Why can an Euler tour tree not directly compute path minimums between two vertices u and v?
In the Euler tour sequence of a tree, walking from u to v traverses not only the simple path between u and v, but also detours completely into and out of every intermediate sibling subtree hanging off that path. For an invertible group operation such as addition or XOR, one can store +w(x) at first(x) and โw(x) at last(x) so that any completely traversed off-path subtree cancels to zero (+w(x) โ w(x) = 0). However, for a non-invertible semigroup operation such as min or max, off-path subtree excursions cannot be canceled out of the prefix interval, requiring a link-cut tree or top tree instead.
How many BST nodes are required to represent a forest of n vertices in an Euler tour tree?
In the directed-arc plus vertex-self-loop representation, each of the n vertices contributes 1 self-loop node (v, v) and each of the at most n โ 1 undirected forest edges contributes 2 directed arc nodes (u, v) and (v, u), requiring at most n + 2(n โ 1) = 3n โ 2 BST nodes in total. All n vertex nodes can be pre-allocated in a static array, and the 2(n โ 1) arc nodes can be drawn from a fixed-size pool in O(n) total memory.
References
- Tarjan, R. E., & Vishkin, U. (1985). "An efficient parallel biconnectivity algorithm." SIAM Journal on Computing, 14(4), 862โ874. https://doi.org/10.1137/0214061
- Henzinger, M. R., & King, V. (1999). "Randomized fully dynamic graph algorithms with polylogarithmic time per operation." Journal of the ACM, 46(4), 502โ516 (Preliminary version in STOC 1995, 519โ527). https://doi.org/10.1145/320211.320215
- Holm, J., de Lichtenberg, K., & Thorup, M. (2001). "Poly-logarithmic deterministic fully-dynamic algorithms for connectivity, minimum spanning tree, 2-edge, and biconnectivity." Journal of the ACM, 48(4), 723โ760. https://doi.org/10.1145/502090.502095
- Sleator, D. D., & Tarjan, R. E. (1983). "A data structure for dynamic trees." Journal of Computer and System Sciences, 26(3), 362โ391. https://doi.org/10.1016/0022-0000(83)90006-590006-5)
- Wulff-Nilsen, C. (2013). "Faster deterministic fully-dynamic graph connectivity." Proceedings of the 24th Annual ACM-SIAM Symposium on Discrete Algorithms (SODA), 1757โ1769. https://doi.org/10.1137/1.9781611973105.126