31
31
//! variable only once, and it does so as soon as it can, so it is reasonable to ask what the type
32
32
//! inferencer knows "so far".
33
33
use super :: InferCtxt ;
34
+ use rustc_data_structures:: fx:: FxHashMap ;
34
35
use rustc_middle:: infer:: unify_key:: ToType ;
35
36
use rustc_middle:: ty:: fold:: TypeFolder ;
36
37
use rustc_middle:: ty:: { self , Ty , TyCtxt , TypeFoldable , TypeSuperFoldable , TypeVisitableExt } ;
38
+ use std:: collections:: hash_map:: Entry ;
37
39
38
40
pub struct TypeFreshener < ' a , ' tcx > {
39
41
infcx : & ' a InferCtxt < ' tcx > ,
40
42
ty_freshen_count : u32 ,
41
43
const_freshen_count : u32 ,
42
- ty_freshen_key_vec : Vec < ty:: InferTy > ,
43
- ty_freshen_value_vec : Vec < Ty < ' tcx > > ,
44
- const_freshen_key_vec : Vec < ty:: InferConst > ,
45
- const_freshen_value_vec : Vec < ty:: Const < ' tcx > > ,
44
+ ty_freshen_map : FxHashMap < ty:: InferTy , Ty < ' tcx > > ,
45
+ const_freshen_map : FxHashMap < ty:: InferConst , ty:: Const < ' tcx > > ,
46
46
}
47
47
48
48
impl < ' a , ' tcx > TypeFreshener < ' a , ' tcx > {
@@ -51,10 +51,8 @@ impl<'a, 'tcx> TypeFreshener<'a, 'tcx> {
51
51
infcx,
52
52
ty_freshen_count : 0 ,
53
53
const_freshen_count : 0 ,
54
- ty_freshen_key_vec : Vec :: new ( ) ,
55
- ty_freshen_value_vec : Vec :: new ( ) ,
56
- const_freshen_key_vec : Vec :: new ( ) ,
57
- const_freshen_value_vec : Vec :: new ( ) ,
54
+ ty_freshen_map : Default :: default ( ) ,
55
+ const_freshen_map : Default :: default ( ) ,
58
56
}
59
57
}
60
58
@@ -66,15 +64,15 @@ impl<'a, 'tcx> TypeFreshener<'a, 'tcx> {
66
64
return ty. fold_with ( self ) ;
67
65
}
68
66
69
- if let Some ( idx ) = self . ty_freshen_key_vec . iter ( ) . position ( |infty| * infty == key) {
70
- unsafe { * self . ty_freshen_value_vec . get_unchecked ( idx ) }
71
- } else {
72
- let index = self . ty_freshen_count ;
73
- self . ty_freshen_count += 1 ;
74
- let t = mk_fresh ( index) ;
75
- self . ty_freshen_key_vec . push ( key ) ;
76
- self . ty_freshen_value_vec . push ( t ) ;
77
- t
67
+ match self . ty_freshen_map . entry ( key) {
68
+ Entry :: Occupied ( entry ) => * entry . get ( ) ,
69
+ Entry :: Vacant ( entry ) => {
70
+ let index = self . ty_freshen_count ;
71
+ self . ty_freshen_count += 1 ;
72
+ let t = mk_fresh ( index) ;
73
+ entry . insert ( t ) ;
74
+ t
75
+ }
78
76
}
79
77
}
80
78
@@ -92,15 +90,15 @@ impl<'a, 'tcx> TypeFreshener<'a, 'tcx> {
92
90
return ct. fold_with ( self ) ;
93
91
}
94
92
95
- if let Some ( idx ) = self . const_freshen_key_vec . iter ( ) . position ( |infty| * infty == key) {
96
- unsafe { * self . const_freshen_value_vec . get_unchecked ( idx ) }
97
- } else {
98
- let index: u32 = self . const_freshen_count ;
99
- self . const_freshen_count += 1 ;
100
- let ct = ty:: Const :: new_infer ( self . infcx . tcx , freshener ( index) , ty) ;
101
- self . const_freshen_key_vec . push ( key ) ;
102
- self . const_freshen_value_vec . push ( ct ) ;
103
- ct
93
+ match self . const_freshen_map . entry ( key) {
94
+ Entry :: Occupied ( entry ) => * entry . get ( ) ,
95
+ Entry :: Vacant ( entry ) => {
96
+ let index = self . const_freshen_count ;
97
+ self . const_freshen_count += 1 ;
98
+ let ct = ty:: Const :: new_infer ( self . infcx . tcx , freshener ( index) , ty) ;
99
+ entry . insert ( ct ) ;
100
+ ct
101
+ }
104
102
}
105
103
}
106
104
}
0 commit comments