@@ -937,6 +937,7 @@ impl<K, V, E, T: Traverse<E> + DoubleEndedIterator<TraversalItem<K, V, E>>>
937
937
// making these arbitrary sub-range iterators. However the logic to construct these paths
938
938
// efficiently is fairly involved, so this is a FIXME. The sub-range iterators also wouldn't be
939
939
// able to accurately predict size, so those iterators can't implement ExactSizeIterator.
940
+ #[ inline]
940
941
fn next ( & mut self ) -> Option < ( K , V ) > {
941
942
loop {
942
943
// We want the smallest element, so try to get the top of the left stack
@@ -1030,6 +1031,7 @@ impl<K, V, E, T: Traverse<E> + DoubleEndedIterator<TraversalItem<K, V, E>>>
1030
1031
}
1031
1032
1032
1033
impl < ' a , K , V > Iterator < ( & ' a K , & ' a V ) > for Entries < ' a , K , V > {
1034
+ #[ inline]
1033
1035
fn next ( & mut self ) -> Option < ( & ' a K , & ' a V ) > { self . inner . next ( ) }
1034
1036
fn size_hint ( & self ) -> ( uint , Option < uint > ) { self . inner . size_hint ( ) }
1035
1037
}
@@ -1040,20 +1042,24 @@ impl<'a, K, V> ExactSizeIterator<(&'a K, &'a V)> for Entries<'a, K, V> {}
1040
1042
1041
1043
1042
1044
impl < ' a , K , V > Iterator < ( & ' a K , & ' a mut V ) > for MutEntries < ' a , K , V > {
1045
+ #[ inline]
1043
1046
fn next ( & mut self ) -> Option < ( & ' a K , & ' a mut V ) > { self . inner . next ( ) }
1044
1047
fn size_hint ( & self ) -> ( uint , Option < uint > ) { self . inner . size_hint ( ) }
1045
1048
}
1046
1049
impl < ' a , K , V > DoubleEndedIterator < ( & ' a K , & ' a mut V ) > for MutEntries < ' a , K , V > {
1050
+ #[ inline]
1047
1051
fn next_back ( & mut self ) -> Option < ( & ' a K , & ' a mut V ) > { self . inner . next_back ( ) }
1048
1052
}
1049
1053
impl < ' a , K , V > ExactSizeIterator < ( & ' a K , & ' a mut V ) > for MutEntries < ' a , K , V > { }
1050
1054
1051
1055
1052
1056
impl < K , V > Iterator < ( K , V ) > for MoveEntries < K , V > {
1057
+ #[ inline]
1053
1058
fn next ( & mut self ) -> Option < ( K , V ) > { self . inner . next ( ) }
1054
1059
fn size_hint ( & self ) -> ( uint , Option < uint > ) { self . inner . size_hint ( ) }
1055
1060
}
1056
1061
impl < K , V > DoubleEndedIterator < ( K , V ) > for MoveEntries < K , V > {
1062
+ #[ inline]
1057
1063
fn next_back ( & mut self ) -> Option < ( K , V ) > { self . inner . next_back ( ) }
1058
1064
}
1059
1065
impl < K , V > ExactSizeIterator < ( K , V ) > for MoveEntries < K , V > { }
@@ -1130,6 +1136,25 @@ impl<K, V> BTreeMap<K, V> {
1130
1136
}
1131
1137
}
1132
1138
1139
+ /// An intrusive version of `.iter()`. The closure will be called once with
1140
+ /// every key/value pair in the tree.
1141
+ ///
1142
+ /// This is faster than calling `.iter()`, but is far less composable.
1143
+ #[ inline]
1144
+ #[ experimental = "relies on unboxed closures" ]
1145
+ pub fn intrusive_iter < F : FnMut ( & K , & V ) > ( & self , mut f : F ) {
1146
+ fn intrusive_iter_impl < K , V , F : FnMut ( & K , & V ) > ( node : & Node < K , V > , f : & mut F ) {
1147
+ for ti in node. iter ( ) {
1148
+ match ti {
1149
+ Elem ( k, v) => ( * f) ( k, v) ,
1150
+ Edge ( e) => intrusive_iter_impl ( e, f) ,
1151
+ }
1152
+ }
1153
+ }
1154
+
1155
+ intrusive_iter_impl ( & self . root , & mut f) ;
1156
+ }
1157
+
1133
1158
/// Gets a mutable iterator over the entries of the map.
1134
1159
#[ unstable = "matches collection reform specification, waiting for dust to settle" ]
1135
1160
pub fn iter_mut < ' a > ( & ' a mut self ) -> MutEntries < ' a , K , V > {
@@ -1144,6 +1169,25 @@ impl<K, V> BTreeMap<K, V> {
1144
1169
}
1145
1170
}
1146
1171
1172
+ /// An intrusive version of `.iter_mut()`. The closure will be called once
1173
+ /// with every key/value pair in the tree.
1174
+ ///
1175
+ /// This is faster than calling `.iter_mut()`, but is far less composable.
1176
+ #[ inline]
1177
+ #[ experimental = "relies on unboxed closures" ]
1178
+ pub fn intrusive_iter_mut < F : FnMut ( & K , & mut V ) > ( & mut self , mut f : F ) {
1179
+ fn intrusive_iter_mut_impl < K , V , F : FnMut ( & K , & mut V ) > ( node : & mut Node < K , V > , f : & mut F ) {
1180
+ for ti in node. iter_mut ( ) {
1181
+ match ti {
1182
+ Elem ( k, v) => ( * f) ( k, v) ,
1183
+ Edge ( e) => intrusive_iter_mut_impl ( e, f) ,
1184
+ }
1185
+ }
1186
+ }
1187
+
1188
+ intrusive_iter_mut_impl ( & mut self . root , & mut f) ;
1189
+ }
1190
+
1147
1191
/// Gets an owning iterator over the entries of the map.
1148
1192
#[ unstable = "matches collection reform specification, waiting for dust to settle" ]
1149
1193
pub fn into_iter ( self ) -> MoveEntries < K , V > {
@@ -1158,6 +1202,25 @@ impl<K, V> BTreeMap<K, V> {
1158
1202
}
1159
1203
}
1160
1204
1205
+ /// An intrusive version of `.into_iter()`. The closure will be called once
1206
+ /// with every key/value pair in the tree.
1207
+ ///
1208
+ /// This is faster than calling `.into_iter()`, but is far less composable.
1209
+ #[ inline]
1210
+ #[ experimental = "relies on unboxed closures" ]
1211
+ pub fn intrusive_into_iter < F : FnMut ( K , V ) > ( self , mut f : F ) {
1212
+ fn intrusive_into_iter_impl < K , V , F : FnMut ( K , V ) > ( node : Node < K , V > , f : & mut F ) {
1213
+ for ti in node. into_iter ( ) {
1214
+ match ti {
1215
+ Elem ( k, v) => ( * f) ( k, v) ,
1216
+ Edge ( e) => intrusive_into_iter_impl ( e, f) ,
1217
+ }
1218
+ }
1219
+ }
1220
+
1221
+ intrusive_into_iter_impl ( self . root , & mut f) ;
1222
+ }
1223
+
1161
1224
/// Gets an iterator over the keys of the map.
1162
1225
///
1163
1226
/// # Examples
@@ -1580,4 +1643,34 @@ mod bench {
1580
1643
pub fn iter_100000 ( b : & mut Bencher ) {
1581
1644
bench_iter ( b, 100000 ) ;
1582
1645
}
1646
+
1647
+ fn bench_intrusive_iter ( b : & mut Bencher , size : uint ) {
1648
+ let mut map = BTreeMap :: < uint , uint > :: new ( ) ;
1649
+ let mut rng = weak_rng ( ) ;
1650
+
1651
+ for _ in range ( 0 , size) {
1652
+ map. insert ( rng. gen ( ) , rng. gen ( ) ) ;
1653
+ }
1654
+
1655
+ b. iter ( || {
1656
+ map. intrusive_iter ( |& mut : k, v| {
1657
+ black_box ( k) ; black_box ( v) ;
1658
+ } ) ;
1659
+ } ) ;
1660
+ }
1661
+
1662
+ #[ bench]
1663
+ pub fn intrusive_iter_20 ( b : & mut Bencher ) {
1664
+ bench_intrusive_iter ( b, 20 ) ;
1665
+ }
1666
+
1667
+ #[ bench]
1668
+ pub fn intrusive_iter_1000 ( b : & mut Bencher ) {
1669
+ bench_intrusive_iter ( b, 1000 ) ;
1670
+ }
1671
+
1672
+ #[ bench]
1673
+ pub fn intrusive_iter_100000 ( b : & mut Bencher ) {
1674
+ bench_intrusive_iter ( b, 100000 ) ;
1675
+ }
1583
1676
}
0 commit comments