Optimization: don't push forest edges if there are no non-forest edges

This optimizes the process of searching for a replacement edge to refrain from pushing forest edges down when a tree does not have any same-level non-forest edges. If a tree doesn't have any such edges, then there definitely isn't a replacement edge at that level, so we can avoid doing extra work.

Interestingly, with this optimization, ConnGraph reduces to a single Euler tour forest if the graph is a forest, with addEdge and removeEdge taking O(log N) (non-amortized) time with high probability.
This commit is contained in:
William Jacobs
2019-03-06 22:24:50 -05:00
parent a60eac5b6c
commit 1536209eb3
5 changed files with 16 additions and 11 deletions

View File

@@ -829,17 +829,22 @@ public class ConnGraph {
while (levelVertex1 != null) {
EulerTourNode root1 = levelVertex1.arbitraryVisit.root();
EulerTourNode root2 = levelVertex2.arbitraryVisit.root();
EulerTourNode root;
if (root1.size < root2.size) {
root = root1;
} else {
root = root2;
}
pushForestEdges(root);
replacementEdge = findReplacementEdge(root);
if (replacementEdge != null) {
break;
// Optimization: if hasGraphEdge is false for one of the roots, then there definitely isn't a
// replacement edge at this level
if (root1.hasGraphEdge && root2.hasGraphEdge) {
EulerTourNode root;
if (root1.size < root2.size) {
root = root1;
} else {
root = root2;
}
pushForestEdges(root);
replacementEdge = findReplacementEdge(root);
if (replacementEdge != null) {
break;
}
}
// To save space, get rid of trees with one node