@@ -70,67 +70,64 @@ impl<I: Idx> IntervalSet<I> {
70
70
/// Returns true if we increased the number of elements present.
71
71
pub fn insert_range ( & mut self , range : impl RangeBounds < I > + Clone ) -> bool {
72
72
let start = inclusive_start ( range. clone ( ) ) ;
73
- let Some ( mut end) = inclusive_end ( self . domain , range) else {
73
+ let Some ( end) = inclusive_end ( self . domain , range) else {
74
74
// empty range
75
75
return false ;
76
76
} ;
77
77
if start > end {
78
78
return false ;
79
79
}
80
80
81
- loop {
82
- // This condition looks a bit weird, but actually makes sense.
83
- //
84
- // if r.0 == end + 1, then we're actually adjacent, so we want to
85
- // continue to the next range. We're looking here for the first
86
- // range which starts *non-adjacently* to our end.
87
- let next = self . map . partition_point ( |r| r. 0 <= end + 1 ) ;
88
- if let Some ( last) = next. checked_sub ( 1 ) {
89
- let ( prev_start, prev_end) = & mut self . map [ last] ;
90
- if * prev_end + 1 >= start {
91
- // If the start for the inserted range is adjacent to the
92
- // end of the previous, we can extend the previous range.
93
- if start < * prev_start {
94
- // Our range starts before the one we found. We'll need
95
- // to *remove* it, and then try again.
96
- //
97
- // FIXME: This is not so efficient; we may need to
98
- // recurse a bunch of times here. Instead, it's probably
99
- // better to do something like drain_filter(...) on the
100
- // map to be able to delete or modify all the ranges in
101
- // start..=end and then potentially re-insert a new
102
- // range.
103
- end = std:: cmp:: max ( end, * prev_end) ;
104
- self . map . remove ( last) ;
105
- } else {
106
- // We overlap with the previous range, increase it to
107
- // include us.
108
- //
109
- // Make sure we're actually going to *increase* it though --
110
- // it may be that end is just inside the previously existing
111
- // set.
112
- return if end > * prev_end {
113
- * prev_end = end;
114
- true
115
- } else {
116
- false
117
- } ;
81
+ // This condition looks a bit weird, but actually makes sense.
82
+ //
83
+ // if r.0 == end + 1, then we're actually adjacent, so we want to
84
+ // continue to the next range. We're looking here for the first
85
+ // range which starts *non-adjacently* to our end.
86
+ let next = self . map . partition_point ( |r| r. 0 <= end + 1 ) ;
87
+ if let Some ( right) = next. checked_sub ( 1 ) {
88
+ let ( prev_start, prev_end) = self . map [ right] ;
89
+ if prev_end + 1 >= start {
90
+ // If the start for the inserted range is adjacent to the
91
+ // end of the previous, we can extend the previous range.
92
+ if start < prev_start {
93
+ // The first range which ends *non-adjacently* to our start.
94
+ // And we can ensure that left <= right.
95
+ let left = self . map . partition_point ( |l| l. 1 + 1 < start) ;
96
+ let min = std:: cmp:: min ( self . map [ left] . 0 , start) ;
97
+ let max = std:: cmp:: max ( prev_end, end) ;
98
+ self . map [ right] = ( min, max) ;
99
+ if left != right {
100
+ self . map . drain ( left..right) ;
118
101
}
119
- } else {
120
- // Otherwise, we don't overlap, so just insert
121
- self . map . insert ( last + 1 , ( start, end) ) ;
122
102
return true ;
123
- }
124
- } else {
125
- if self . map . is_empty ( ) {
126
- // Quite common in practice, and expensive to call memcpy
127
- // with length zero.
128
- self . map . push ( ( start, end) ) ;
129
103
} else {
130
- self . map . insert ( next, ( start, end) ) ;
104
+ // We overlap with the previous range, increase it to
105
+ // include us.
106
+ //
107
+ // Make sure we're actually going to *increase* it though --
108
+ // it may be that end is just inside the previously existing
109
+ // set.
110
+ return if end > prev_end {
111
+ self . map [ right] . 1 = end;
112
+ true
113
+ } else {
114
+ false
115
+ } ;
131
116
}
117
+ } else {
118
+ // Otherwise, we don't overlap, so just insert
119
+ self . map . insert ( right + 1 , ( start, end) ) ;
132
120
return true ;
133
121
}
122
+ } else {
123
+ if self . map . is_empty ( ) {
124
+ // Quite common in practice, and expensive to call memcpy
125
+ // with length zero.
126
+ self . map . push ( ( start, end) ) ;
127
+ } else {
128
+ self . map . insert ( next, ( start, end) ) ;
129
+ }
130
+ return true ;
134
131
}
135
132
}
136
133
0 commit comments