@@ -1545,16 +1545,10 @@ impl<K, V> IntoIterator for BTreeMap<K, V> {
15451545
15461546 fn into_iter ( self ) -> IntoIter < K , V > {
15471547 let mut me = ManuallyDrop :: new ( self ) ;
1548- if let Some ( root) = me. root . as_mut ( ) {
1549- let root1 = unsafe { ptr:: read ( root) . into_ref ( ) } ;
1550- let root2 = unsafe { ptr:: read ( root) . into_ref ( ) } ;
1551- let len = me. length ;
1552-
1553- IntoIter {
1554- front : Some ( root1. first_leaf_edge ( ) ) ,
1555- back : Some ( root2. last_leaf_edge ( ) ) ,
1556- length : len,
1557- }
1548+ if let Some ( root) = me. root . take ( ) {
1549+ let ( f, b) = full_range_search ( root. into_ref ( ) ) ;
1550+
1551+ IntoIter { front : Some ( f) , back : Some ( b) , length : me. length }
15581552 } else {
15591553 IntoIter { front : None , back : None , length : 0 }
15601554 }
@@ -2042,6 +2036,7 @@ where
20422036 }
20432037}
20442038
2039+ /// Finds the leaf edges delimiting a specified range in or underneath a node.
20452040fn range_search < BorrowType , K , V , Q : ?Sized , R : RangeBounds < Q > > (
20462041 root1 : NodeRef < BorrowType , K , V , marker:: LeafOrInternal > ,
20472042 root2 : NodeRef < BorrowType , K , V , marker:: LeafOrInternal > ,
@@ -2126,6 +2121,33 @@ where
21262121 }
21272122}
21282123
2124+ /// Equivalent to `range_search(k, v, ..)` without the `Ord` bound.
2125+ fn full_range_search < BorrowType , K , V > (
2126+ root : NodeRef < BorrowType , K , V , marker:: LeafOrInternal > ,
2127+ ) -> (
2128+ Handle < NodeRef < BorrowType , K , V , marker:: Leaf > , marker:: Edge > ,
2129+ Handle < NodeRef < BorrowType , K , V , marker:: Leaf > , marker:: Edge > ,
2130+ ) {
2131+ // We duplicate the root NodeRef here -- we will never access it in a way
2132+ // that overlaps references obtained from the root.
2133+ let mut min_node = unsafe { ptr:: read ( & root) } ;
2134+ let mut max_node = root;
2135+ loop {
2136+ let front = min_node. first_edge ( ) ;
2137+ let back = max_node. last_edge ( ) ;
2138+ match ( front. force ( ) , back. force ( ) ) {
2139+ ( Leaf ( f) , Leaf ( b) ) => {
2140+ return ( f, b) ;
2141+ }
2142+ ( Internal ( min_int) , Internal ( max_int) ) => {
2143+ min_node = min_int. descend ( ) ;
2144+ max_node = max_int. descend ( ) ;
2145+ }
2146+ _ => unreachable ! ( "BTreeMap has different depths" ) ,
2147+ } ;
2148+ }
2149+ }
2150+
21292151impl < K , V > BTreeMap < K , V > {
21302152 /// Gets an iterator over the entries of the map, sorted by key.
21312153 ///
@@ -2150,12 +2172,12 @@ impl<K, V> BTreeMap<K, V> {
21502172 /// ```
21512173 #[ stable( feature = "rust1" , since = "1.0.0" ) ]
21522174 pub fn iter ( & self ) -> Iter < ' _ , K , V > {
2153- Iter {
2154- range : Range {
2155- front : self . root . as_ref ( ) . map ( |r| r . as_ref ( ) . first_leaf_edge ( ) ) ,
2156- back : self . root . as_ref ( ) . map ( |r| r . as_ref ( ) . last_leaf_edge ( ) ) ,
2157- } ,
2158- length : self . length ,
2175+ if let Some ( root ) = & self . root {
2176+ let ( f , b ) = full_range_search ( root . as_ref ( ) ) ;
2177+
2178+ Iter { range : Range { front : Some ( f ) , back : Some ( b ) } , length : self . length }
2179+ } else {
2180+ Iter { range : Range { front : None , back : None } , length : 0 }
21592181 }
21602182 }
21612183
@@ -2182,19 +2204,15 @@ impl<K, V> BTreeMap<K, V> {
21822204 /// ```
21832205 #[ stable( feature = "rust1" , since = "1.0.0" ) ]
21842206 pub fn iter_mut ( & mut self ) -> IterMut < ' _ , K , V > {
2185- IterMut {
2186- range : if let Some ( root) = & mut self . root {
2187- let root1 = root. as_mut ( ) ;
2188- let root2 = unsafe { ptr:: read ( & root1) } ;
2189- RangeMut {
2190- front : Some ( root1. first_leaf_edge ( ) ) ,
2191- back : Some ( root2. last_leaf_edge ( ) ) ,
2192- _marker : PhantomData ,
2193- }
2194- } else {
2195- RangeMut { front : None , back : None , _marker : PhantomData }
2196- } ,
2197- length : self . length ,
2207+ if let Some ( root) = & mut self . root {
2208+ let ( f, b) = full_range_search ( root. as_mut ( ) ) ;
2209+
2210+ IterMut {
2211+ range : RangeMut { front : Some ( f) , back : Some ( b) , _marker : PhantomData } ,
2212+ length : self . length ,
2213+ }
2214+ } else {
2215+ IterMut { range : RangeMut { front : None , back : None , _marker : PhantomData } , length : 0 }
21982216 }
21992217 }
22002218
0 commit comments