[iter_without_into_iter]: fix papercuts + only lint on pub types

This commit is contained in:
y21 2023-10-22 14:05:01 +02:00
parent 2b030eb03d
commit 3c501e4e41
5 changed files with 357 additions and 355 deletions

View file

@ -104,6 +104,12 @@ fn is_nameable_in_impl_trait(ty: &rustc_hir::Ty<'_>) -> bool {
!matches!(ty.kind, TyKind::OpaqueDef(..)) !matches!(ty.kind, TyKind::OpaqueDef(..))
} }
fn is_ty_exported(cx: &LateContext<'_>, ty: Ty<'_>) -> bool {
ty.ty_adt_def()
.and_then(|adt| adt.did().as_local())
.is_some_and(|did| cx.effective_visibilities.is_exported(did))
}
/// Returns the deref chain of a type, starting with the type itself. /// Returns the deref chain of a type, starting with the type itself.
fn deref_chain<'cx, 'tcx>(cx: &'cx LateContext<'tcx>, ty: Ty<'tcx>) -> impl Iterator<Item = Ty<'tcx>> + 'cx { fn deref_chain<'cx, 'tcx>(cx: &'cx LateContext<'tcx>, ty: Ty<'tcx>) -> impl Iterator<Item = Ty<'tcx>> + 'cx {
iter::successors(Some(ty), |&ty| { iter::successors(Some(ty), |&ty| {
@ -154,6 +160,7 @@ impl LateLintPass<'_> for IterWithoutIntoIter {
None None
} }
}) })
&& is_ty_exported(cx, ty)
{ {
span_lint_and_then( span_lint_and_then(
cx, cx,
@ -226,6 +233,7 @@ impl {self_ty_without_ref} {{
) )
// Only lint if the `IntoIterator` impl doesn't actually exist // Only lint if the `IntoIterator` impl doesn't actually exist
&& !implements_trait(cx, ref_ty, into_iter_did, &[]) && !implements_trait(cx, ref_ty, into_iter_did, &[])
&& is_ty_exported(cx, ref_ty.peel_refs())
{ {
let self_ty_snippet = format!("{borrow_prefix}{}", snippet(cx, imp.self_ty.span, "..")); let self_ty_snippet = format!("{borrow_prefix}{}", snippet(cx, imp.self_ty.span, ".."));
@ -247,8 +255,8 @@ impl {self_ty_without_ref} {{
" "
impl IntoIterator for {self_ty_snippet} {{ impl IntoIterator for {self_ty_snippet} {{
type IntoIter = {ret_ty}; type IntoIter = {ret_ty};
type Iter = {iter_ty}; type Item = {iter_ty};
fn into_iter() -> Self::IntoIter {{ fn into_iter(self) -> Self::IntoIter {{
self.iter() self.iter()
}} }}
}} }}

View file

@ -3,127 +3,117 @@
use std::iter::IntoIterator; use std::iter::IntoIterator;
fn main() { pub struct S1;
{ impl<'a> IntoIterator for &'a S1 {
struct S; //~^ ERROR: `IntoIterator` implemented for a reference type without an `iter` method
type IntoIter = std::slice::Iter<'a, u8>;
impl<'a> IntoIterator for &'a S { type Item = &'a u8;
//~^ ERROR: `IntoIterator` implemented for a reference type without an `iter` method fn into_iter(self) -> Self::IntoIter {
type IntoIter = std::slice::Iter<'a, u8>; todo!()
type Item = &'a u8;
fn into_iter(self) -> Self::IntoIter {
todo!()
}
}
impl<'a> IntoIterator for &'a mut S {
//~^ ERROR: `IntoIterator` implemented for a reference type without an `iter_mut` method
type IntoIter = std::slice::IterMut<'a, u8>;
type Item = &'a mut u8;
fn into_iter(self) -> Self::IntoIter {
todo!()
}
}
} }
{ }
struct S<T>(T); impl<'a> IntoIterator for &'a mut S1 {
impl<'a, T> IntoIterator for &'a S<T> { //~^ ERROR: `IntoIterator` implemented for a reference type without an `iter_mut` method
//~^ ERROR: `IntoIterator` implemented for a reference type without an `iter` method type IntoIter = std::slice::IterMut<'a, u8>;
type IntoIter = std::slice::Iter<'a, T>; type Item = &'a mut u8;
type Item = &'a T; fn into_iter(self) -> Self::IntoIter {
fn into_iter(self) -> Self::IntoIter { todo!()
todo!()
}
}
impl<'a, T> IntoIterator for &'a mut S<T> {
//~^ ERROR: `IntoIterator` implemented for a reference type without an `iter_mut` method
type IntoIter = std::slice::IterMut<'a, T>;
type Item = &'a mut T;
fn into_iter(self) -> Self::IntoIter {
todo!()
}
}
}
{
// Both iter and iter_mut methods exist, don't lint
struct S<'a, T>(&'a T);
impl<'a, T> S<'a, T> {
fn iter(&self) -> std::slice::Iter<'a, T> {
todo!()
}
fn iter_mut(&mut self) -> std::slice::IterMut<'a, T> {
todo!()
}
}
impl<'a, T> IntoIterator for &S<'a, T> {
type IntoIter = std::slice::Iter<'a, T>;
type Item = &'a T;
fn into_iter(self) -> Self::IntoIter {
todo!()
}
}
impl<'a, T> IntoIterator for &mut S<'a, T> {
type IntoIter = std::slice::IterMut<'a, T>;
type Item = &'a mut T;
fn into_iter(self) -> Self::IntoIter {
todo!()
}
}
}
{
// Only `iter` exists, no `iter_mut`
struct S<'a, T>(&'a T);
impl<'a, T> S<'a, T> {
fn iter(&self) -> std::slice::Iter<'a, T> {
todo!()
}
}
impl<'a, T> IntoIterator for &S<'a, T> {
type IntoIter = std::slice::Iter<'a, T>;
type Item = &'a T;
fn into_iter(self) -> Self::IntoIter {
todo!()
}
}
impl<'a, T> IntoIterator for &mut S<'a, T> {
//~^ ERROR: `IntoIterator` implemented for a reference type without an `iter_mut` method
type IntoIter = std::slice::IterMut<'a, T>;
type Item = &'a mut T;
fn into_iter(self) -> Self::IntoIter {
todo!()
}
}
}
{
// `iter` exists, but `IntoIterator` is implemented for an alias. inherent_impls doesn't "normalize"
// aliases so that `inherent_impls(Alias)` where `type Alias = S` returns nothing, so this can lead
// to fun FPs. Make sure it doesn't happen here (we're using type_of, which should skip the alias).
struct S;
impl S {
fn iter(&self) -> std::slice::Iter<'static, u8> {
todo!()
}
}
type Alias = S;
impl IntoIterator for &Alias {
type IntoIter = std::slice::Iter<'static, u8>;
type Item = &'static u8;
fn into_iter(self) -> Self::IntoIter {
todo!()
}
}
} }
} }
fn issue11635() { pub struct S2<T>(T);
impl<'a, T> IntoIterator for &'a S2<T> {
//~^ ERROR: `IntoIterator` implemented for a reference type without an `iter` method
type IntoIter = std::slice::Iter<'a, T>;
type Item = &'a T;
fn into_iter(self) -> Self::IntoIter {
todo!()
}
}
impl<'a, T> IntoIterator for &'a mut S2<T> {
//~^ ERROR: `IntoIterator` implemented for a reference type without an `iter_mut` method
type IntoIter = std::slice::IterMut<'a, T>;
type Item = &'a mut T;
fn into_iter(self) -> Self::IntoIter {
todo!()
}
}
// Both iter and iter_mut methods exist, don't lint
pub struct S3<'a, T>(&'a T);
impl<'a, T> S3<'a, T> {
fn iter(&self) -> std::slice::Iter<'a, T> {
todo!()
}
fn iter_mut(&mut self) -> std::slice::IterMut<'a, T> {
todo!()
}
}
impl<'a, T> IntoIterator for &S3<'a, T> {
type IntoIter = std::slice::Iter<'a, T>;
type Item = &'a T;
fn into_iter(self) -> Self::IntoIter {
todo!()
}
}
impl<'a, T> IntoIterator for &mut S3<'a, T> {
type IntoIter = std::slice::IterMut<'a, T>;
type Item = &'a mut T;
fn into_iter(self) -> Self::IntoIter {
todo!()
}
}
// Only `iter` exists, no `iter_mut`
pub struct S4<'a, T>(&'a T);
impl<'a, T> S4<'a, T> {
fn iter(&self) -> std::slice::Iter<'a, T> {
todo!()
}
}
impl<'a, T> IntoIterator for &S4<'a, T> {
type IntoIter = std::slice::Iter<'a, T>;
type Item = &'a T;
fn into_iter(self) -> Self::IntoIter {
todo!()
}
}
impl<'a, T> IntoIterator for &mut S4<'a, T> {
//~^ ERROR: `IntoIterator` implemented for a reference type without an `iter_mut` method
type IntoIter = std::slice::IterMut<'a, T>;
type Item = &'a mut T;
fn into_iter(self) -> Self::IntoIter {
todo!()
}
}
// `iter` exists, but `IntoIterator` is implemented for an alias. inherent_impls doesn't "normalize"
// aliases so that `inherent_impls(Alias)` where `type Alias = S` returns nothing, so this can lead
// to fun FPs. Make sure it doesn't happen here (we're using type_of, which should skip the alias).
pub struct S5;
impl S5 {
fn iter(&self) -> std::slice::Iter<'static, u8> {
todo!()
}
}
pub type Alias = S5;
impl IntoIterator for &Alias {
type IntoIter = std::slice::Iter<'static, u8>;
type Item = &'static u8;
fn into_iter(self) -> Self::IntoIter {
todo!()
}
}
fn main() {}
pub mod issue11635 {
// A little more involved than the original repro in the issue, but this tests that it correctly // A little more involved than the original repro in the issue, but this tests that it correctly
// works for more than one deref step // works for more than one deref step

View file

@ -1,21 +1,21 @@
error: `IntoIterator` implemented for a reference type without an `iter` method error: `IntoIterator` implemented for a reference type without an `iter` method
--> $DIR/into_iter_without_iter.rs:10:9 --> $DIR/into_iter_without_iter.rs:7:1
| |
LL | / impl<'a> IntoIterator for &'a S { LL | / impl<'a> IntoIterator for &'a S1 {
LL | | LL | |
LL | | type IntoIter = std::slice::Iter<'a, u8>; LL | | type IntoIter = std::slice::Iter<'a, u8>;
LL | | type Item = &'a u8; LL | | type Item = &'a u8;
... | ... |
LL | | } LL | | }
LL | | } LL | | }
| |_________^ | |_^
| |
= note: `-D clippy::into-iter-without-iter` implied by `-D warnings` = note: `-D clippy::into-iter-without-iter` implied by `-D warnings`
= help: to override `-D warnings` add `#[allow(clippy::into_iter_without_iter)]` = help: to override `-D warnings` add `#[allow(clippy::into_iter_without_iter)]`
help: consider implementing `iter` help: consider implementing `iter`
| |
LL ~ LL +
LL + impl S { LL + impl S1 {
LL + fn iter(&self) -> std::slice::Iter<'a, u8> { LL + fn iter(&self) -> std::slice::Iter<'a, u8> {
LL + <&Self as IntoIterator>::into_iter(self) LL + <&Self as IntoIterator>::into_iter(self)
LL + } LL + }
@ -23,21 +23,21 @@ LL + }
| |
error: `IntoIterator` implemented for a reference type without an `iter_mut` method error: `IntoIterator` implemented for a reference type without an `iter_mut` method
--> $DIR/into_iter_without_iter.rs:18:9 --> $DIR/into_iter_without_iter.rs:15:1
| |
LL | / impl<'a> IntoIterator for &'a mut S { LL | / impl<'a> IntoIterator for &'a mut S1 {
LL | | LL | |
LL | | type IntoIter = std::slice::IterMut<'a, u8>; LL | | type IntoIter = std::slice::IterMut<'a, u8>;
LL | | type Item = &'a mut u8; LL | | type Item = &'a mut u8;
... | ... |
LL | | } LL | | }
LL | | } LL | | }
| |_________^ | |_^
| |
help: consider implementing `iter_mut` help: consider implementing `iter_mut`
| |
LL ~ LL +
LL + impl S { LL + impl S1 {
LL + fn iter_mut(&mut self) -> std::slice::IterMut<'a, u8> { LL + fn iter_mut(&mut self) -> std::slice::IterMut<'a, u8> {
LL + <&mut Self as IntoIterator>::into_iter(self) LL + <&mut Self as IntoIterator>::into_iter(self)
LL + } LL + }
@ -45,21 +45,21 @@ LL + }
| |
error: `IntoIterator` implemented for a reference type without an `iter` method error: `IntoIterator` implemented for a reference type without an `iter` method
--> $DIR/into_iter_without_iter.rs:29:9 --> $DIR/into_iter_without_iter.rs:25:1
| |
LL | / impl<'a, T> IntoIterator for &'a S<T> { LL | / impl<'a, T> IntoIterator for &'a S2<T> {
LL | | LL | |
LL | | type IntoIter = std::slice::Iter<'a, T>; LL | | type IntoIter = std::slice::Iter<'a, T>;
LL | | type Item = &'a T; LL | | type Item = &'a T;
... | ... |
LL | | } LL | | }
LL | | } LL | | }
| |_________^ | |_^
| |
help: consider implementing `iter` help: consider implementing `iter`
| |
LL ~ LL +
LL + impl S<T> { LL + impl S2<T> {
LL + fn iter(&self) -> std::slice::Iter<'a, T> { LL + fn iter(&self) -> std::slice::Iter<'a, T> {
LL + <&Self as IntoIterator>::into_iter(self) LL + <&Self as IntoIterator>::into_iter(self)
LL + } LL + }
@ -67,21 +67,21 @@ LL + }
| |
error: `IntoIterator` implemented for a reference type without an `iter_mut` method error: `IntoIterator` implemented for a reference type without an `iter_mut` method
--> $DIR/into_iter_without_iter.rs:37:9 --> $DIR/into_iter_without_iter.rs:33:1
| |
LL | / impl<'a, T> IntoIterator for &'a mut S<T> { LL | / impl<'a, T> IntoIterator for &'a mut S2<T> {
LL | | LL | |
LL | | type IntoIter = std::slice::IterMut<'a, T>; LL | | type IntoIter = std::slice::IterMut<'a, T>;
LL | | type Item = &'a mut T; LL | | type Item = &'a mut T;
... | ... |
LL | | } LL | | }
LL | | } LL | | }
| |_________^ | |_^
| |
help: consider implementing `iter_mut` help: consider implementing `iter_mut`
| |
LL ~ LL +
LL + impl S<T> { LL + impl S2<T> {
LL + fn iter_mut(&mut self) -> std::slice::IterMut<'a, T> { LL + fn iter_mut(&mut self) -> std::slice::IterMut<'a, T> {
LL + <&mut Self as IntoIterator>::into_iter(self) LL + <&mut Self as IntoIterator>::into_iter(self)
LL + } LL + }
@ -89,21 +89,21 @@ LL + }
| |
error: `IntoIterator` implemented for a reference type without an `iter_mut` method error: `IntoIterator` implemented for a reference type without an `iter_mut` method
--> $DIR/into_iter_without_iter.rs:93:9 --> $DIR/into_iter_without_iter.rs:84:1
| |
LL | / impl<'a, T> IntoIterator for &mut S<'a, T> { LL | / impl<'a, T> IntoIterator for &mut S4<'a, T> {
LL | | LL | |
LL | | type IntoIter = std::slice::IterMut<'a, T>; LL | | type IntoIter = std::slice::IterMut<'a, T>;
LL | | type Item = &'a mut T; LL | | type Item = &'a mut T;
... | ... |
LL | | } LL | | }
LL | | } LL | | }
| |_________^ | |_^
| |
help: consider implementing `iter_mut` help: consider implementing `iter_mut`
| |
LL ~ LL +
LL + impl S<'a, T> { LL + impl S4<'a, T> {
LL + fn iter_mut(&mut self) -> std::slice::IterMut<'a, T> { LL + fn iter_mut(&mut self) -> std::slice::IterMut<'a, T> {
LL + <&mut Self as IntoIterator>::into_iter(self) LL + <&mut Self as IntoIterator>::into_iter(self)
LL + } LL + }

View file

@ -1,120 +1,124 @@
//@no-rustfix //@no-rustfix
#![warn(clippy::iter_without_into_iter)] #![warn(clippy::iter_without_into_iter)]
fn main() { pub struct S1;
{ impl S1 {
struct S; pub fn iter(&self) -> std::slice::Iter<'_, u8> {
impl S { //~^ ERROR: `iter` method without an `IntoIterator` impl
pub fn iter(&self) -> std::slice::Iter<'_, u8> { [].iter()
//~^ ERROR: `iter` method without an `IntoIterator` impl
[].iter()
}
pub fn iter_mut(&mut self) -> std::slice::IterMut<'_, u8> {
//~^ ERROR: `iter_mut` method without an `IntoIterator` impl
[].iter_mut()
}
}
} }
{ pub fn iter_mut(&mut self) -> std::slice::IterMut<'_, u8> {
struct S; //~^ ERROR: `iter_mut` method without an `IntoIterator` impl
impl S { [].iter_mut()
pub fn iter(&self) -> impl Iterator<Item = &u8> {
// RPITIT is not stable, so we can't generally suggest it here yet
[].iter()
}
}
}
{
struct S<'a>(&'a mut [u8]);
impl<'a> S<'a> {
pub fn iter(&self) -> std::slice::Iter<'_, u8> {
//~^ ERROR: `iter` method without an `IntoIterator` impl
self.0.iter()
}
pub fn iter_mut(&mut self) -> std::slice::IterMut<'_, u8> {
//~^ ERROR: `iter_mut` method without an `IntoIterator` impl
self.0.iter_mut()
}
}
}
{
// Incompatible signatures
struct S;
impl S {
pub fn iter(self) -> std::slice::Iter<'static, u8> {
todo!()
}
}
struct S2;
impl S2 {
pub async fn iter(&self) -> std::slice::Iter<'static, u8> {
todo!()
}
}
struct S3;
impl S3 {
pub fn iter(&self, _additional_param: ()) -> std::slice::Iter<'static, u8> {
todo!()
}
}
struct S4<T>(T);
impl<T> S4<T> {
pub fn iter<U>(&self) -> std::slice::Iter<'static, (T, U)> {
todo!()
}
}
struct S5<T>(T);
impl<T> S5<T> {
pub fn iter(&self) -> std::slice::Iter<'static, T> {
todo!()
}
}
}
{
struct S<T>(T);
impl<T> S<T> {
pub fn iter(&self) -> std::slice::Iter<'_, T> {
//~^ ERROR: `iter` method without an `IntoIterator` impl
todo!()
}
pub fn iter_mut(&mut self) -> std::slice::IterMut<'_, T> {
//~^ ERROR: `iter_mut` method without an `IntoIterator` impl
todo!()
}
}
}
{
struct S<T>(T);
impl<T> S<T> {
pub fn iter(&self) -> std::slice::Iter<'_, T> {
// Don't lint, there's an existing (wrong) IntoIterator impl
todo!()
}
}
impl<'a, T> IntoIterator for &'a S<T> {
type Item = &'a String;
type IntoIter = std::slice::Iter<'a, String>;
fn into_iter(self) -> Self::IntoIter {
todo!()
}
}
}
{
struct S<T>(T);
impl<T> S<T> {
pub fn iter_mut(&self) -> std::slice::IterMut<'_, T> {
// Don't lint, there's an existing (wrong) IntoIterator impl
todo!()
}
}
impl<'a, T> IntoIterator for &'a mut S<T> {
type Item = &'a mut String;
type IntoIter = std::slice::IterMut<'a, String>;
fn into_iter(self) -> Self::IntoIter {
todo!()
}
}
} }
} }
pub struct S2;
impl S2 {
pub fn iter(&self) -> impl Iterator<Item = &u8> {
// RPITIT is not stable, so we can't generally suggest it here yet
[].iter()
}
}
pub struct S3<'a>(&'a mut [u8]);
impl<'a> S3<'a> {
pub fn iter(&self) -> std::slice::Iter<'_, u8> {
//~^ ERROR: `iter` method without an `IntoIterator` impl
self.0.iter()
}
pub fn iter_mut(&mut self) -> std::slice::IterMut<'_, u8> {
//~^ ERROR: `iter_mut` method without an `IntoIterator` impl
self.0.iter_mut()
}
}
// Incompatible signatures
pub struct S4;
impl S4 {
pub fn iter(self) -> std::slice::Iter<'static, u8> {
todo!()
}
}
pub struct S5;
impl S5 {
pub async fn iter(&self) -> std::slice::Iter<'static, u8> {
todo!()
}
}
pub struct S6;
impl S6 {
pub fn iter(&self, _additional_param: ()) -> std::slice::Iter<'static, u8> {
todo!()
}
}
pub struct S7<T>(T);
impl<T> S7<T> {
pub fn iter<U>(&self) -> std::slice::Iter<'static, (T, U)> {
todo!()
}
}
pub struct S8<T>(T);
impl<T> S8<T> {
pub fn iter(&self) -> std::slice::Iter<'static, T> {
todo!()
}
}
// ===========================
pub struct S9<T>(T);
impl<T> S9<T> {
pub fn iter(&self) -> std::slice::Iter<'_, T> {
//~^ ERROR: `iter` method without an `IntoIterator` impl
todo!()
}
pub fn iter_mut(&mut self) -> std::slice::IterMut<'_, T> {
//~^ ERROR: `iter_mut` method without an `IntoIterator` impl
todo!()
}
}
pub struct S10<T>(T);
impl<T> S10<T> {
pub fn iter(&self) -> std::slice::Iter<'_, T> {
// Don't lint, there's an existing (wrong) IntoIterator impl
todo!()
}
}
impl<'a, T> IntoIterator for &'a S10<T> {
type Item = &'a String;
type IntoIter = std::slice::Iter<'a, String>;
fn into_iter(self) -> Self::IntoIter {
todo!()
}
}
pub struct S11<T>(T);
impl<T> S11<T> {
pub fn iter_mut(&self) -> std::slice::IterMut<'_, T> {
// Don't lint, there's an existing (wrong) IntoIterator impl
todo!()
}
}
impl<'a, T> IntoIterator for &'a mut S11<T> {
type Item = &'a mut String;
type IntoIter = std::slice::IterMut<'a, String>;
fn into_iter(self) -> Self::IntoIter {
todo!()
}
}
// Private type not exported: don't lint
struct S12;
impl S12 {
fn iter(&self) -> std::slice::Iter<'_, u8> {
todo!()
}
}
fn main() {}

View file

@ -1,146 +1,146 @@
error: `iter` method without an `IntoIterator` impl for `&S` error: `iter` method without an `IntoIterator` impl for `&S1`
--> $DIR/iter_without_into_iter.rs:8:13 --> $DIR/iter_without_into_iter.rs:6:5
| |
LL | / pub fn iter(&self) -> std::slice::Iter<'_, u8> { LL | / pub fn iter(&self) -> std::slice::Iter<'_, u8> {
LL | | LL | |
LL | | [].iter() LL | | [].iter()
LL | | } LL | | }
| |_____________^ | |_____^
| |
= note: `-D clippy::iter-without-into-iter` implied by `-D warnings` = note: `-D clippy::iter-without-into-iter` implied by `-D warnings`
= help: to override `-D warnings` add `#[allow(clippy::iter_without_into_iter)]` = help: to override `-D warnings` add `#[allow(clippy::iter_without_into_iter)]`
help: consider implementing `IntoIterator` for `&S` help: consider implementing `IntoIterator` for `&S1`
| |
LL ~ LL +
LL + impl IntoIterator for &S { LL + impl IntoIterator for &S1 {
LL + type IntoIter = std::slice::Iter<'_, u8>; LL + type IntoIter = std::slice::Iter<'_, u8>;
LL + type Iter = &u8; LL + type Item = &u8;
LL + fn into_iter() -> Self::IntoIter { LL + fn into_iter(self) -> Self::IntoIter {
LL + self.iter() LL + self.iter()
LL + } LL + }
LL + } LL + }
| |
error: `iter_mut` method without an `IntoIterator` impl for `&mut S` error: `iter_mut` method without an `IntoIterator` impl for `&mut S1`
--> $DIR/iter_without_into_iter.rs:12:13 --> $DIR/iter_without_into_iter.rs:10:5
| |
LL | / pub fn iter_mut(&mut self) -> std::slice::IterMut<'_, u8> { LL | / pub fn iter_mut(&mut self) -> std::slice::IterMut<'_, u8> {
LL | | LL | |
LL | | [].iter_mut() LL | | [].iter_mut()
LL | | } LL | | }
| |_____________^ | |_____^
| |
help: consider implementing `IntoIterator` for `&mut S` help: consider implementing `IntoIterator` for `&mut S1`
| |
LL ~ LL +
LL + impl IntoIterator for &mut S { LL + impl IntoIterator for &mut S1 {
LL + type IntoIter = std::slice::IterMut<'_, u8>; LL + type IntoIter = std::slice::IterMut<'_, u8>;
LL + type Iter = &mut u8; LL + type Item = &mut u8;
LL + fn into_iter() -> Self::IntoIter { LL + fn into_iter(self) -> Self::IntoIter {
LL + self.iter() LL + self.iter()
LL + } LL + }
LL + } LL + }
| |
error: `iter` method without an `IntoIterator` impl for `&S<'a>` error: `iter` method without an `IntoIterator` impl for `&S3<'a>`
--> $DIR/iter_without_into_iter.rs:30:13 --> $DIR/iter_without_into_iter.rs:26:5
| |
LL | / pub fn iter(&self) -> std::slice::Iter<'_, u8> { LL | / pub fn iter(&self) -> std::slice::Iter<'_, u8> {
LL | | LL | |
LL | | self.0.iter() LL | | self.0.iter()
LL | | } LL | | }
| |_____________^ | |_____^
| |
help: consider implementing `IntoIterator` for `&S<'a>` help: consider implementing `IntoIterator` for `&S3<'a>`
| |
LL ~ LL +
LL + impl IntoIterator for &S<'a> { LL + impl IntoIterator for &S3<'a> {
LL + type IntoIter = std::slice::Iter<'_, u8>; LL + type IntoIter = std::slice::Iter<'_, u8>;
LL + type Iter = &u8; LL + type Item = &u8;
LL + fn into_iter() -> Self::IntoIter { LL + fn into_iter(self) -> Self::IntoIter {
LL + self.iter() LL + self.iter()
LL + } LL + }
LL + } LL + }
| |
error: `iter_mut` method without an `IntoIterator` impl for `&mut S<'a>` error: `iter_mut` method without an `IntoIterator` impl for `&mut S3<'a>`
--> $DIR/iter_without_into_iter.rs:34:13 --> $DIR/iter_without_into_iter.rs:30:5
| |
LL | / pub fn iter_mut(&mut self) -> std::slice::IterMut<'_, u8> { LL | / pub fn iter_mut(&mut self) -> std::slice::IterMut<'_, u8> {
LL | | LL | |
LL | | self.0.iter_mut() LL | | self.0.iter_mut()
LL | | } LL | | }
| |_____________^ | |_____^
| |
help: consider implementing `IntoIterator` for `&mut S<'a>` help: consider implementing `IntoIterator` for `&mut S3<'a>`
| |
LL ~ LL +
LL + impl IntoIterator for &mut S<'a> { LL + impl IntoIterator for &mut S3<'a> {
LL + type IntoIter = std::slice::IterMut<'_, u8>; LL + type IntoIter = std::slice::IterMut<'_, u8>;
LL + type Iter = &mut u8; LL + type Item = &mut u8;
LL + fn into_iter() -> Self::IntoIter { LL + fn into_iter(self) -> Self::IntoIter {
LL + self.iter() LL + self.iter()
LL + } LL + }
LL + } LL + }
| |
error: `iter` method without an `IntoIterator` impl for `&S5<T>` error: `iter` method without an `IntoIterator` impl for `&S8<T>`
--> $DIR/iter_without_into_iter.rs:68:13 --> $DIR/iter_without_into_iter.rs:67:5
| |
LL | / pub fn iter(&self) -> std::slice::Iter<'static, T> { LL | / pub fn iter(&self) -> std::slice::Iter<'static, T> {
LL | | todo!() LL | | todo!()
LL | | } LL | | }
| |_____________^ | |_____^
| |
help: consider implementing `IntoIterator` for `&S5<T>` help: consider implementing `IntoIterator` for `&S8<T>`
| |
LL ~ LL +
LL + impl IntoIterator for &S5<T> { LL + impl IntoIterator for &S8<T> {
LL + type IntoIter = std::slice::Iter<'static, T>; LL + type IntoIter = std::slice::Iter<'static, T>;
LL + type Iter = &T; LL + type Item = &T;
LL + fn into_iter() -> Self::IntoIter { LL + fn into_iter(self) -> Self::IntoIter {
LL + self.iter() LL + self.iter()
LL + } LL + }
LL + } LL + }
| |
error: `iter` method without an `IntoIterator` impl for `&S<T>` error: `iter` method without an `IntoIterator` impl for `&S9<T>`
--> $DIR/iter_without_into_iter.rs:76:13 --> $DIR/iter_without_into_iter.rs:75:5
| |
LL | / pub fn iter(&self) -> std::slice::Iter<'_, T> { LL | / pub fn iter(&self) -> std::slice::Iter<'_, T> {
LL | | LL | |
LL | | todo!() LL | | todo!()
LL | | } LL | | }
| |_____________^ | |_____^
| |
help: consider implementing `IntoIterator` for `&S<T>` help: consider implementing `IntoIterator` for `&S9<T>`
| |
LL ~ LL +
LL + impl IntoIterator for &S<T> { LL + impl IntoIterator for &S9<T> {
LL + type IntoIter = std::slice::Iter<'_, T>; LL + type IntoIter = std::slice::Iter<'_, T>;
LL + type Iter = &T; LL + type Item = &T;
LL + fn into_iter() -> Self::IntoIter { LL + fn into_iter(self) -> Self::IntoIter {
LL + self.iter() LL + self.iter()
LL + } LL + }
LL + } LL + }
| |
error: `iter_mut` method without an `IntoIterator` impl for `&mut S<T>` error: `iter_mut` method without an `IntoIterator` impl for `&mut S9<T>`
--> $DIR/iter_without_into_iter.rs:80:13 --> $DIR/iter_without_into_iter.rs:79:5
| |
LL | / pub fn iter_mut(&mut self) -> std::slice::IterMut<'_, T> { LL | / pub fn iter_mut(&mut self) -> std::slice::IterMut<'_, T> {
LL | | LL | |
LL | | todo!() LL | | todo!()
LL | | } LL | | }
| |_____________^ | |_____^
| |
help: consider implementing `IntoIterator` for `&mut S<T>` help: consider implementing `IntoIterator` for `&mut S9<T>`
| |
LL ~ LL +
LL + impl IntoIterator for &mut S<T> { LL + impl IntoIterator for &mut S9<T> {
LL + type IntoIter = std::slice::IterMut<'_, T>; LL + type IntoIter = std::slice::IterMut<'_, T>;
LL + type Iter = &mut T; LL + type Item = &mut T;
LL + fn into_iter() -> Self::IntoIter { LL + fn into_iter(self) -> Self::IntoIter {
LL + self.iter() LL + self.iter()
LL + } LL + }
LL + } LL + }