Priority-trie: merge edges with different priorities into ranges when possible.
This commit is contained in:
@@ -10,7 +10,7 @@
|
|||||||
(A2B (A.A1 _ (B.B1 x)))
|
(A2B (A.A1 _ (B.B1 x)))
|
||||||
(B.B1 x))
|
(B.B1 x))
|
||||||
|
|
||||||
(rule 1
|
(rule 0
|
||||||
(A2B (A.A1 (B.B1 x) _))
|
(A2B (A.A1 (B.B1 x) _))
|
||||||
(B.B1 x))
|
(B.B1 x))
|
||||||
|
|
||||||
|
|||||||
@@ -301,12 +301,21 @@ impl TrieNode {
|
|||||||
|
|
||||||
// Now find or insert the appropriate edge.
|
// Now find or insert the appropriate edge.
|
||||||
let mut edge: Option<usize> = None;
|
let mut edge: Option<usize> = None;
|
||||||
for i in 0..edges.len() {
|
let mut last_edge_with_op: Option<usize> = None;
|
||||||
if edges[i].range.contains(prio) && edges[i].symbol == op {
|
let mut last_edge_with_op_prio: Option<Prio> = None;
|
||||||
edge = Some(i);
|
for i in 0..(edges.len() + 1) {
|
||||||
break;
|
if i == edges.len() || prio > edges[i].range.1 {
|
||||||
}
|
// We've passed all edges with overlapping priority
|
||||||
if prio > edges[i].range.1 {
|
// ranges. Maybe the last edge we saw with the op
|
||||||
|
// we're inserting can have its range expanded,
|
||||||
|
// however.
|
||||||
|
if last_edge_with_op.is_some() && edges[last_edge_with_op.unwrap()].symbol == op {
|
||||||
|
// Move it to the end of the run of equal-unit-range ops.
|
||||||
|
edges.swap(last_edge_with_op.unwrap(), i - 1);
|
||||||
|
edge = Some(i - 1);
|
||||||
|
edges[i - 1].range.1 = prio;
|
||||||
|
break;
|
||||||
|
}
|
||||||
edges.insert(
|
edges.insert(
|
||||||
i,
|
i,
|
||||||
TrieEdge {
|
TrieEdge {
|
||||||
@@ -318,15 +327,25 @@ impl TrieNode {
|
|||||||
edge = Some(i);
|
edge = Some(i);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
if i == edges.len() {
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
if edges[i].symbol == op {
|
||||||
|
last_edge_with_op = Some(i);
|
||||||
|
last_edge_with_op_prio = Some(edges[i].range.1);
|
||||||
|
}
|
||||||
|
if last_edge_with_op_prio.is_some()
|
||||||
|
&& last_edge_with_op_prio.unwrap() < edges[i].range.1
|
||||||
|
{
|
||||||
|
last_edge_with_op = None;
|
||||||
|
last_edge_with_op_prio = None;
|
||||||
|
}
|
||||||
|
if edges[i].range.contains(prio) && edges[i].symbol == op {
|
||||||
|
edge = Some(i);
|
||||||
|
break;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
let edge = edge.unwrap_or_else(|| {
|
let edge = edge.expect("Must have found an edge at least at last iter");
|
||||||
edges.push(TrieEdge {
|
|
||||||
range: PrioRange(prio, prio),
|
|
||||||
symbol: op.clone(),
|
|
||||||
node: TrieNode::Empty,
|
|
||||||
});
|
|
||||||
edges.len() - 1
|
|
||||||
});
|
|
||||||
let edge = &mut edges[edge];
|
let edge = &mut edges[edge];
|
||||||
|
|
||||||
if is_last {
|
if is_last {
|
||||||
|
|||||||
Reference in New Issue
Block a user