diff options
| author | Ariel Ben-Yehuda <arielb1@mail.tau.ac.il> | 2017-04-22 15:05:18 +0300 |
|---|---|---|
| committer | Ariel Ben-Yehuda <ariel.byd@gmail.com> | 2017-04-22 21:02:50 +0300 |
| commit | a660ad84b3c27de5c0abfb683fb178ba4e4ca87e (patch) | |
| tree | 93665674d9ec3bbe6fa88502a81c6c32a0a592f0 | |
| parent | a0f145ba8c96feb25ae059e0917c55ef6dae01e8 (diff) | |
| download | rust-a660ad84b3c27de5c0abfb683fb178ba4e4ca87e.tar.gz rust-a660ad84b3c27de5c0abfb683fb178ba4e4ca87e.zip | |
bail out of selection when there are multiple surviving candidates
In some cases (e.g. <[int-var] as Add<[int-var]>>), selection can turn up a large number of candidates. Bailing out early avoids O(n^2) performance. This improves item-type checking time by quite a bit, resulting in ~2% of total time-to-typeck.
| -rw-r--r-- | src/librustc/traits/select.rs | 14 |
1 files changed, 7 insertions, 7 deletions
diff --git a/src/librustc/traits/select.rs b/src/librustc/traits/select.rs index 70ddcff5181..6442487ead9 100644 --- a/src/librustc/traits/select.rs +++ b/src/librustc/traits/select.rs @@ -943,17 +943,17 @@ impl<'cx, 'gcx, 'tcx> SelectionContext<'cx, 'gcx, 'tcx> { debug!("Retaining candidate #{}/{}: {:?}", i, candidates.len(), candidates[i]); i += 1; + + // If there are *STILL* multiple candidates, give up + // and report ambiguity. + if i > 1 { + debug!("multiple matches, ambig"); + return Ok(None); + } } } } - // If there are *STILL* multiple candidates, give up and - // report ambiguity. - if candidates.len() > 1 { - debug!("multiple matches, ambig"); - return Ok(None); - } - // If there are *NO* candidates, then there are no impls -- // that we know of, anyway. Note that in the case where there // are unbound type variables within the obligation, it might |
