Skip to content

Commit a21c2eb

Browse files
committed
Iterate over the smaller list
If there are two lists of different sizes, iterating over the smaller list and then looking up in the larger list is cheaper than vice versa, because lookups scale sublinearly.
1 parent 4d247ad commit a21c2eb

File tree

2 files changed

+12
-0
lines changed

2 files changed

+12
-0
lines changed

compiler/rustc_middle/src/ty/mod.rs

+4
Original file line numberDiff line numberDiff line change
@@ -265,6 +265,10 @@ impl<'tcx> AssociatedItems<'tcx> {
265265
self.items.iter().map(|(_, v)| *v)
266266
}
267267

268+
pub fn len(&self) -> usize {
269+
self.items.len()
270+
}
271+
268272
/// Returns an iterator over all associated items with the given name, ignoring hygiene.
269273
pub fn filter_by_name_unhygienic(
270274
&self,

compiler/rustc_typeck/src/coherence/inherent_impls_overlap.rs

+8
Original file line numberDiff line numberDiff line change
@@ -22,6 +22,14 @@ impl InherentOverlapChecker<'tcx> {
2222
let impl_items1 = self.tcx.associated_items(impl1);
2323
let impl_items2 = self.tcx.associated_items(impl2);
2424

25+
let mut impl_items1 = &impl_items1;
26+
let mut impl_items2 = &impl_items2;
27+
28+
// Performance optimization: iterate over the smaller list
29+
if impl_items1.len() > impl_items2.len() {
30+
std::mem::swap(&mut impl_items1, &mut impl_items2);
31+
}
32+
2533
for item1 in impl_items1.in_definition_order() {
2634
let collision = impl_items2.filter_by_name_unhygienic(item1.ident.name).any(|item2| {
2735
// Symbols and namespace match, compare hygienically.

0 commit comments

Comments
 (0)