Be more lax in .into_iter()
suggestion when encountering Iterator
methods on non-Iterator
``` error[E0599]: no method named `map` found for struct `Vec<bool>` in the current scope --> $DIR/vec-on-unimplemented.rs:3:23 | LL | vec![true, false].map(|v| !v).collect::<Vec<_>>(); | ^^^ `Vec<bool>` is not an iterator | help: call `.into_iter()` first | LL | vec![true, false].into_iter().map(|v| !v).collect::<Vec<_>>(); | ++++++++++++ ``` We used to provide some help through `rustc_on_unimplemented` on non-`impl Trait` and non-type-params, but this lets us get rid of some otherwise unnecessary conditions in the annotation on `Iterator`.
This commit is contained in:
parent
f0c93117ed
commit
89a3c19832
@ -166,7 +166,7 @@ fn is_iterator_predicate(predicate: ty::Predicate<'_>, tcx: TyCtxt<'_>) -> bool
|
|||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
match ty.kind() {
|
match ty.peel_refs().kind() {
|
||||||
ty::Param(param) => {
|
ty::Param(param) => {
|
||||||
let generics = self.tcx.generics_of(self.body_id);
|
let generics = self.tcx.generics_of(self.body_id);
|
||||||
let generic_param = generics.type_param(¶m, self.tcx);
|
let generic_param = generics.type_param(¶m, self.tcx);
|
||||||
@ -184,7 +184,7 @@ fn is_iterator_predicate(predicate: ty::Predicate<'_>, tcx: TyCtxt<'_>) -> bool
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
ty::Alias(ty::AliasKind::Opaque, _) => {
|
ty::Slice(..) | ty::Adt(..) | ty::Alias(ty::AliasKind::Opaque, _) => {
|
||||||
for unsatisfied in unsatisfied_predicates.iter() {
|
for unsatisfied in unsatisfied_predicates.iter() {
|
||||||
if is_iterator_predicate(unsatisfied.0, self.tcx) {
|
if is_iterator_predicate(unsatisfied.0, self.tcx) {
|
||||||
return true;
|
return true;
|
||||||
|
@ -34,15 +34,6 @@ fn _assert_is_object_safe(_: &dyn Iterator<Item = ()>) {}
|
|||||||
_Self = "core::ops::range::RangeToInclusive<Idx>",
|
_Self = "core::ops::range::RangeToInclusive<Idx>",
|
||||||
note = "you might have meant to use a bounded `RangeInclusive`"
|
note = "you might have meant to use a bounded `RangeInclusive`"
|
||||||
),
|
),
|
||||||
on(
|
|
||||||
_Self = "[]",
|
|
||||||
label = "`{Self}` is not an iterator; try calling `.into_iter()` or `.iter()`"
|
|
||||||
),
|
|
||||||
on(_Self = "&[]", label = "`{Self}` is not an iterator; try calling `.iter()`"),
|
|
||||||
on(
|
|
||||||
_Self = "alloc::vec::Vec<T, A>",
|
|
||||||
label = "`{Self}` is not an iterator; try calling `.into_iter()` or `.iter()`"
|
|
||||||
),
|
|
||||||
label = "`{Self}` is not an iterator",
|
label = "`{Self}` is not an iterator",
|
||||||
message = "`{Self}` is not an iterator"
|
message = "`{Self}` is not an iterator"
|
||||||
)]
|
)]
|
||||||
|
5
tests/ui/iterators/vec-on-unimplemented.fixed
Normal file
5
tests/ui/iterators/vec-on-unimplemented.fixed
Normal file
@ -0,0 +1,5 @@
|
|||||||
|
//@ run-rustfix
|
||||||
|
fn main() {
|
||||||
|
let _ = vec![true, false].into_iter().map(|v| !v).collect::<Vec<_>>();
|
||||||
|
//~^ ERROR no method named `map` found for struct `Vec<bool>` in the current scope
|
||||||
|
}
|
@ -1,4 +1,5 @@
|
|||||||
|
//@ run-rustfix
|
||||||
fn main() {
|
fn main() {
|
||||||
vec![true, false].map(|v| !v).collect::<Vec<_>>();
|
let _ = vec![true, false].map(|v| !v).collect::<Vec<_>>();
|
||||||
//~^ ERROR `Vec<bool>` is not an iterator
|
//~^ ERROR no method named `map` found for struct `Vec<bool>` in the current scope
|
||||||
}
|
}
|
||||||
|
@ -1,14 +1,13 @@
|
|||||||
error[E0599]: `Vec<bool>` is not an iterator
|
error[E0599]: no method named `map` found for struct `Vec<bool>` in the current scope
|
||||||
--> $DIR/vec-on-unimplemented.rs:2:23
|
--> $DIR/vec-on-unimplemented.rs:3:31
|
||||||
|
|
|
|
||||||
LL | vec![true, false].map(|v| !v).collect::<Vec<_>>();
|
LL | let _ = vec![true, false].map(|v| !v).collect::<Vec<_>>();
|
||||||
| ^^^ `Vec<bool>` is not an iterator; try calling `.into_iter()` or `.iter()`
|
| ^^^ `Vec<bool>` is not an iterator
|
||||||
|
|
|
|
||||||
= note: the following trait bounds were not satisfied:
|
help: call `.into_iter()` first
|
||||||
`Vec<bool>: Iterator`
|
|
|
||||||
which is required by `&mut Vec<bool>: Iterator`
|
LL | let _ = vec![true, false].into_iter().map(|v| !v).collect::<Vec<_>>();
|
||||||
`[bool]: Iterator`
|
| ++++++++++++
|
||||||
which is required by `&mut [bool]: Iterator`
|
|
||||||
|
|
||||||
error: aborting due to 1 previous error
|
error: aborting due to 1 previous error
|
||||||
|
|
||||||
|
8
tests/ui/methods/issues/issue-94581.fixed
Normal file
8
tests/ui/methods/issues/issue-94581.fixed
Normal file
@ -0,0 +1,8 @@
|
|||||||
|
//@ run-rustfix
|
||||||
|
fn get_slice() -> &'static [i32] {
|
||||||
|
&[1, 2, 3, 4]
|
||||||
|
}
|
||||||
|
|
||||||
|
fn main() {
|
||||||
|
let _sqsum: i32 = get_slice().into_iter().map(|i| i * i).sum(); //~ ERROR [E0599]
|
||||||
|
}
|
@ -1,7 +1,8 @@
|
|||||||
|
//@ run-rustfix
|
||||||
fn get_slice() -> &'static [i32] {
|
fn get_slice() -> &'static [i32] {
|
||||||
&[1, 2, 3, 4]
|
&[1, 2, 3, 4]
|
||||||
}
|
}
|
||||||
|
|
||||||
fn main() {
|
fn main() {
|
||||||
let sqsum = get_slice().map(|i| i * i).sum(); //~ ERROR [E0599]
|
let _sqsum: i32 = get_slice().map(|i| i * i).sum(); //~ ERROR [E0599]
|
||||||
}
|
}
|
||||||
|
@ -1,14 +1,13 @@
|
|||||||
error[E0599]: `&'static [i32]` is not an iterator
|
error[E0599]: no method named `map` found for reference `&'static [i32]` in the current scope
|
||||||
--> $DIR/issue-94581.rs:6:29
|
--> $DIR/issue-94581.rs:7:35
|
||||||
|
|
|
|
||||||
LL | let sqsum = get_slice().map(|i| i * i).sum();
|
LL | let _sqsum: i32 = get_slice().map(|i| i * i).sum();
|
||||||
| ^^^ `&'static [i32]` is not an iterator; try calling `.iter()`
|
| ^^^ `&'static [i32]` is not an iterator
|
||||||
|
|
|
|
||||||
= note: the following trait bounds were not satisfied:
|
help: call `.into_iter()` first
|
||||||
`&'static [i32]: Iterator`
|
|
|
||||||
which is required by `&mut &'static [i32]: Iterator`
|
LL | let _sqsum: i32 = get_slice().into_iter().map(|i| i * i).sum();
|
||||||
`[i32]: Iterator`
|
| ++++++++++++
|
||||||
which is required by `&mut [i32]: Iterator`
|
|
||||||
|
|
||||||
error: aborting due to 1 previous error
|
error: aborting due to 1 previous error
|
||||||
|
|
||||||
|
@ -14,7 +14,7 @@ struct PriorityQueueEntry<T> {
|
|||||||
//~^ ERROR can't compare `PriorityQueue<T>` with `PriorityQueue<T>`
|
//~^ ERROR can't compare `PriorityQueue<T>` with `PriorityQueue<T>`
|
||||||
//~| ERROR the trait bound `PriorityQueue<T>: Eq` is not satisfied
|
//~| ERROR the trait bound `PriorityQueue<T>: Eq` is not satisfied
|
||||||
//~| ERROR can't compare `T` with `T`
|
//~| ERROR can't compare `T` with `T`
|
||||||
//~| ERROR `BinaryHeap<PriorityQueueEntry<T>>` is not an iterator
|
//~| ERROR no method named `cmp` found for struct `BinaryHeap<PriorityQueueEntry<T>>`
|
||||||
//~| ERROR no field `height` on type `&PriorityQueue<T>`
|
//~| ERROR no field `height` on type `&PriorityQueue<T>`
|
||||||
|
|
||||||
struct PriorityQueue<T>(BinaryHeap<PriorityQueueEntry<T>>);
|
struct PriorityQueue<T>(BinaryHeap<PriorityQueueEntry<T>>);
|
||||||
|
@ -46,15 +46,12 @@ LL | struct PriorityQueue<T>(BinaryHeap<PriorityQueueEntry<T>>);
|
|||||||
= help: the trait `PartialOrd<_>` is not implemented for `BinaryHeap<PriorityQueueEntry<T>>`
|
= help: the trait `PartialOrd<_>` is not implemented for `BinaryHeap<PriorityQueueEntry<T>>`
|
||||||
= note: this error originates in the derive macro `PartialOrd` (in Nightly builds, run with -Z macro-backtrace for more info)
|
= note: this error originates in the derive macro `PartialOrd` (in Nightly builds, run with -Z macro-backtrace for more info)
|
||||||
|
|
||||||
error[E0599]: `BinaryHeap<PriorityQueueEntry<T>>` is not an iterator
|
error[E0599]: no method named `cmp` found for struct `BinaryHeap<PriorityQueueEntry<T>>` in the current scope
|
||||||
--> $DIR/issue-104884-trait-impl-sugg-err.rs:13:22
|
--> $DIR/issue-104884-trait-impl-sugg-err.rs:13:22
|
||||||
|
|
|
|
||||||
LL | #[derive(PartialOrd, AddImpl)]
|
LL | #[derive(PartialOrd, AddImpl)]
|
||||||
| ^^^^^^^ `BinaryHeap<PriorityQueueEntry<T>>` is not an iterator
|
| ^^^^^^^ `BinaryHeap<PriorityQueueEntry<T>>` is not an iterator
|
||||||
|
|
|
|
||||||
= note: the following trait bounds were not satisfied:
|
|
||||||
`BinaryHeap<PriorityQueueEntry<T>>: Iterator`
|
|
||||||
which is required by `&mut BinaryHeap<PriorityQueueEntry<T>>: Iterator`
|
|
||||||
= note: this error originates in the derive macro `AddImpl` (in Nightly builds, run with -Z macro-backtrace for more info)
|
= note: this error originates in the derive macro `AddImpl` (in Nightly builds, run with -Z macro-backtrace for more info)
|
||||||
|
|
||||||
error[E0609]: no field `height` on type `&PriorityQueue<T>`
|
error[E0609]: no field `height` on type `&PriorityQueue<T>`
|
||||||
|
Loading…
Reference in New Issue
Block a user