From fd629c0cde26d727fbc19580455a4efd04a84828 Mon Sep 17 00:00:00 2001 From: kyoto7250 <50972773+kyoto7250@users.noreply.github.com> Date: Thu, 9 Jun 2022 22:34:16 +0900 Subject: [PATCH] check method --- clippy_lints/src/use_retain.rs | 2 +- clippy_utils/src/paths.rs | 1 + tests/ui/use_retain.fixed | 28 +++++++++++++++++ tests/ui/use_retain.rs | 28 +++++++++++++++++ tests/ui/use_retain.stderr | 56 ++++++++++++++++++++++++---------- 5 files changed, 98 insertions(+), 17 deletions(-) diff --git a/clippy_lints/src/use_retain.rs b/clippy_lints/src/use_retain.rs index b55e1006aac..b6b6dc572c1 100644 --- a/clippy_lints/src/use_retain.rs +++ b/clippy_lints/src/use_retain.rs @@ -102,7 +102,7 @@ fn check_iter( if_chain! { if let hir::ExprKind::MethodCall(_, [filter_expr], _) = &target_expr.kind; if let Some(copied_def_id) = cx.typeck_results().type_dependent_def_id(target_expr.hir_id); - if match_def_path(cx, copied_def_id, &paths::CORE_ITER_COPIED); + if match_def_path(cx, copied_def_id, &paths::CORE_ITER_COPIED) || match_def_path(cx, copied_def_id, &paths::CORE_ITER_CLONED); if let hir::ExprKind::MethodCall(_, [iter_expr, _], _) = &filter_expr.kind; if let Some(filter_def_id) = cx.typeck_results().type_dependent_def_id(filter_expr.hir_id); diff --git a/clippy_utils/src/paths.rs b/clippy_utils/src/paths.rs index 17cccd43a9c..a2d5279e397 100644 --- a/clippy_utils/src/paths.rs +++ b/clippy_utils/src/paths.rs @@ -25,6 +25,7 @@ pub const CLONE_TRAIT_METHOD: [&str; 4] = ["core", "clone", "Clone", "clone"]; pub const COW: [&str; 3] = ["alloc", "borrow", "Cow"]; pub const CORE_ITER_COLLECT: [&str; 6] = ["core", "iter", "traits", "iterator", "Iterator", "collect"]; +pub const CORE_ITER_CLONED: [&str; 6] = ["core", "iter", "traits", "iterator", "Iterator", "cloned"]; pub const CORE_ITER_COPIED: [&str; 6] = ["core", "iter", "traits", "iterator", "Iterator", "copied"]; pub const CORE_ITER_FILTER: [&str; 6] = ["core", "iter", "traits", "iterator", "Iterator", "filter"]; pub const CORE_ITER_INTO_ITER: [&str; 6] = ["core", "iter", "traits", "collect", "IntoIterator", "into_iter"]; diff --git a/tests/ui/use_retain.fixed b/tests/ui/use_retain.fixed index d24571b36f8..0c80d0e204a 100644 --- a/tests/ui/use_retain.fixed +++ b/tests/ui/use_retain.fixed @@ -25,10 +25,12 @@ fn binary_heap_retain() { let mut heap = BinaryHeap::from([1, 2, 3]); heap = heap.into_iter().filter(|x| x % 2 == 0).collect(); heap = heap.iter().filter(|&x| x % 2 == 0).copied().collect(); + heap = heap.iter().filter(|&x| x % 2 == 0).cloned().collect(); // Do not lint, because type conversion is performed heap = heap.into_iter().filter(|x| x % 2 == 0).collect::>(); heap = heap.iter().filter(|&x| x % 2 == 0).copied().collect::>(); + heap = heap.iter().filter(|&x| x % 2 == 0).cloned().collect::>(); // Do not lint, because this expression is not assign. let mut bar: BinaryHeap = heap.iter().filter(|&x| x % 2 == 0).copied().collect(); @@ -65,6 +67,7 @@ fn btree_set_retain() { // Do lint. btree_set.retain(|x| x % 2 == 0); btree_set.retain(|x| x % 2 == 0); + btree_set.retain(|x| x % 2 == 0); // Do not lint, because type conversion is performed btree_set = btree_set @@ -73,6 +76,12 @@ fn btree_set_retain() { .copied() .collect::>(); + btree_set = btree_set + .iter() + .filter(|&x| x % 2 == 0) + .cloned() + .collect::>(); + btree_set = btree_set.into_iter().filter(|x| x % 2 == 0).collect::>(); // Do not lint, because this expression is not assign. @@ -81,6 +90,7 @@ fn btree_set_retain() { // Do not lint, because it is an assignment to a different variable. bar = foobar.iter().filter(|&x| x % 2 == 0).copied().collect(); + bar = foobar.iter().filter(|&x| x % 2 == 0).cloned().collect(); bar = foobar.into_iter().filter(|x| x % 2 == 0).collect(); } @@ -109,6 +119,7 @@ fn hash_set_retain() { // Do lint. hash_set.retain(|x| x % 2 == 0); hash_set.retain(|x| x % 2 == 0); + hash_set.retain(|x| x % 2 == 0); // Do not lint, because type conversion is performed hash_set = hash_set.into_iter().filter(|x| x % 2 == 0).collect::>(); @@ -118,12 +129,19 @@ fn hash_set_retain() { .copied() .collect::>(); + hash_set = hash_set + .iter() + .filter(|&x| x % 2 == 0) + .cloned() + .collect::>(); + // Do not lint, because this expression is not assign. let mut bar: HashSet = hash_set.iter().filter(|&x| x % 2 == 0).copied().collect(); let mut foobar: HashSet = hash_set.into_iter().filter(|x| x % 2 == 0).collect(); // Do not lint, because it is an assignment to a different variable. bar = foobar.iter().filter(|&x| x % 2 == 0).copied().collect(); + bar = foobar.iter().filter(|&x| x % 2 == 0).cloned().collect(); bar = foobar.into_iter().filter(|&x| x % 2 == 0).collect(); } @@ -144,10 +162,12 @@ fn vec_retain() { // Do lint. vec.retain(|x| x % 2 == 0); vec.retain(|x| x % 2 == 0); + vec.retain(|x| x % 2 == 0); // Do not lint, because type conversion is performed vec = vec.into_iter().filter(|x| x % 2 == 0).collect::>(); vec = vec.iter().filter(|&x| x % 2 == 0).copied().collect::>(); + vec = vec.iter().filter(|&x| x % 2 == 0).cloned().collect::>(); // Do not lint, because this expression is not assign. let mut bar: Vec = vec.iter().filter(|&x| x % 2 == 0).copied().collect(); @@ -155,6 +175,7 @@ fn vec_retain() { // Do not lint, because it is an assignment to a different variable. bar = foobar.iter().filter(|&x| x % 2 == 0).copied().collect(); + bar = foobar.iter().filter(|&x| x % 2 == 0).cloned().collect(); bar = foobar.into_iter().filter(|x| x % 2 == 0).collect(); } @@ -165,6 +186,7 @@ fn vec_queue_retain() { // Do lint. vec_deque.retain(|x| x % 2 == 0); vec_deque.retain(|x| x % 2 == 0); + vec_deque.retain(|x| x % 2 == 0); // Do not lint, because type conversion is performed vec_deque = vec_deque @@ -172,6 +194,11 @@ fn vec_queue_retain() { .filter(|&x| x % 2 == 0) .copied() .collect::>(); + vec_deque = vec_deque + .iter() + .filter(|&x| x % 2 == 0) + .cloned() + .collect::>(); vec_deque = vec_deque.into_iter().filter(|x| x % 2 == 0).collect::>(); // Do not lint, because this expression is not assign. @@ -180,5 +207,6 @@ fn vec_queue_retain() { // Do not lint, because it is an assignment to a different variable. bar = foobar.iter().filter(|&x| x % 2 == 0).copied().collect(); + bar = foobar.iter().filter(|&x| x % 2 == 0).cloned().collect(); bar = foobar.into_iter().filter(|x| x % 2 == 0).collect(); } diff --git a/tests/ui/use_retain.rs b/tests/ui/use_retain.rs index 4a51825c95f..08c184486f9 100644 --- a/tests/ui/use_retain.rs +++ b/tests/ui/use_retain.rs @@ -25,10 +25,12 @@ fn binary_heap_retain() { let mut heap = BinaryHeap::from([1, 2, 3]); heap = heap.into_iter().filter(|x| x % 2 == 0).collect(); heap = heap.iter().filter(|&x| x % 2 == 0).copied().collect(); + heap = heap.iter().filter(|&x| x % 2 == 0).cloned().collect(); // Do not lint, because type conversion is performed heap = heap.into_iter().filter(|x| x % 2 == 0).collect::>(); heap = heap.iter().filter(|&x| x % 2 == 0).copied().collect::>(); + heap = heap.iter().filter(|&x| x % 2 == 0).cloned().collect::>(); // Do not lint, because this expression is not assign. let mut bar: BinaryHeap = heap.iter().filter(|&x| x % 2 == 0).copied().collect(); @@ -67,6 +69,7 @@ fn btree_set_retain() { // Do lint. btree_set = btree_set.iter().filter(|&x| x % 2 == 0).copied().collect(); + btree_set = btree_set.iter().filter(|&x| x % 2 == 0).cloned().collect(); btree_set = btree_set.into_iter().filter(|x| x % 2 == 0).collect(); // Do not lint, because type conversion is performed @@ -76,6 +79,12 @@ fn btree_set_retain() { .copied() .collect::>(); + btree_set = btree_set + .iter() + .filter(|&x| x % 2 == 0) + .cloned() + .collect::>(); + btree_set = btree_set.into_iter().filter(|x| x % 2 == 0).collect::>(); // Do not lint, because this expression is not assign. @@ -84,6 +93,7 @@ fn btree_set_retain() { // Do not lint, because it is an assignment to a different variable. bar = foobar.iter().filter(|&x| x % 2 == 0).copied().collect(); + bar = foobar.iter().filter(|&x| x % 2 == 0).cloned().collect(); bar = foobar.into_iter().filter(|x| x % 2 == 0).collect(); } @@ -115,6 +125,7 @@ fn hash_set_retain() { // Do lint. hash_set = hash_set.into_iter().filter(|x| x % 2 == 0).collect(); hash_set = hash_set.iter().filter(|&x| x % 2 == 0).copied().collect(); + hash_set = hash_set.iter().filter(|&x| x % 2 == 0).cloned().collect(); // Do not lint, because type conversion is performed hash_set = hash_set.into_iter().filter(|x| x % 2 == 0).collect::>(); @@ -124,12 +135,19 @@ fn hash_set_retain() { .copied() .collect::>(); + hash_set = hash_set + .iter() + .filter(|&x| x % 2 == 0) + .cloned() + .collect::>(); + // Do not lint, because this expression is not assign. let mut bar: HashSet = hash_set.iter().filter(|&x| x % 2 == 0).copied().collect(); let mut foobar: HashSet = hash_set.into_iter().filter(|x| x % 2 == 0).collect(); // Do not lint, because it is an assignment to a different variable. bar = foobar.iter().filter(|&x| x % 2 == 0).copied().collect(); + bar = foobar.iter().filter(|&x| x % 2 == 0).cloned().collect(); bar = foobar.into_iter().filter(|&x| x % 2 == 0).collect(); } @@ -149,11 +167,13 @@ fn vec_retain() { let mut vec = vec![0, 1, 2]; // Do lint. vec = vec.iter().filter(|&x| x % 2 == 0).copied().collect(); + vec = vec.iter().filter(|&x| x % 2 == 0).cloned().collect(); vec = vec.into_iter().filter(|x| x % 2 == 0).collect(); // Do not lint, because type conversion is performed vec = vec.into_iter().filter(|x| x % 2 == 0).collect::>(); vec = vec.iter().filter(|&x| x % 2 == 0).copied().collect::>(); + vec = vec.iter().filter(|&x| x % 2 == 0).cloned().collect::>(); // Do not lint, because this expression is not assign. let mut bar: Vec = vec.iter().filter(|&x| x % 2 == 0).copied().collect(); @@ -161,6 +181,7 @@ fn vec_retain() { // Do not lint, because it is an assignment to a different variable. bar = foobar.iter().filter(|&x| x % 2 == 0).copied().collect(); + bar = foobar.iter().filter(|&x| x % 2 == 0).cloned().collect(); bar = foobar.into_iter().filter(|x| x % 2 == 0).collect(); } @@ -170,6 +191,7 @@ fn vec_queue_retain() { // Do lint. vec_deque = vec_deque.iter().filter(|&x| x % 2 == 0).copied().collect(); + vec_deque = vec_deque.iter().filter(|&x| x % 2 == 0).cloned().collect(); vec_deque = vec_deque.into_iter().filter(|x| x % 2 == 0).collect(); // Do not lint, because type conversion is performed @@ -178,6 +200,11 @@ fn vec_queue_retain() { .filter(|&x| x % 2 == 0) .copied() .collect::>(); + vec_deque = vec_deque + .iter() + .filter(|&x| x % 2 == 0) + .cloned() + .collect::>(); vec_deque = vec_deque.into_iter().filter(|x| x % 2 == 0).collect::>(); // Do not lint, because this expression is not assign. @@ -186,5 +213,6 @@ fn vec_queue_retain() { // Do not lint, because it is an assignment to a different variable. bar = foobar.iter().filter(|&x| x % 2 == 0).copied().collect(); + bar = foobar.iter().filter(|&x| x % 2 == 0).cloned().collect(); bar = foobar.into_iter().filter(|x| x % 2 == 0).collect(); } diff --git a/tests/ui/use_retain.stderr b/tests/ui/use_retain.stderr index 331259c1626..e29d40a2e39 100644 --- a/tests/ui/use_retain.stderr +++ b/tests/ui/use_retain.stderr @@ -1,5 +1,5 @@ error: this expression can be written more simply using `.retain()` - --> $DIR/use_retain.rs:45:5 + --> $DIR/use_retain.rs:47:5 | LL | btree_map = btree_map.into_iter().filter(|(k, _)| k % 2 == 0).collect(); | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: consider calling `.retain()` instead: `btree_map.retain(|k, _| k % 2 == 0)` @@ -7,13 +7,13 @@ LL | btree_map = btree_map.into_iter().filter(|(k, _)| k % 2 == 0).collect() = note: `-D clippy::use-retain` implied by `-D warnings` error: this expression can be written more simply using `.retain()` - --> $DIR/use_retain.rs:46:5 + --> $DIR/use_retain.rs:48:5 | LL | btree_map = btree_map.into_iter().filter(|(_, v)| v % 2 == 0).collect(); | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: consider calling `.retain()` instead: `btree_map.retain(|_, &mut v| v % 2 == 0)` error: this expression can be written more simply using `.retain()` - --> $DIR/use_retain.rs:47:5 + --> $DIR/use_retain.rs:49:5 | LL | / btree_map = btree_map LL | | .into_iter() @@ -22,31 +22,37 @@ LL | | .collect(); | |__________________^ help: consider calling `.retain()` instead: `btree_map.retain(|k, &mut v| (k % 2 == 0) && (v % 2 == 0))` error: this expression can be written more simply using `.retain()` - --> $DIR/use_retain.rs:69:5 + --> $DIR/use_retain.rs:71:5 | LL | btree_set = btree_set.iter().filter(|&x| x % 2 == 0).copied().collect(); | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: consider calling `.retain()` instead: `btree_set.retain(|x| x % 2 == 0)` error: this expression can be written more simply using `.retain()` - --> $DIR/use_retain.rs:70:5 + --> $DIR/use_retain.rs:72:5 + | +LL | btree_set = btree_set.iter().filter(|&x| x % 2 == 0).cloned().collect(); + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: consider calling `.retain()` instead: `btree_set.retain(|x| x % 2 == 0)` + +error: this expression can be written more simply using `.retain()` + --> $DIR/use_retain.rs:73:5 | LL | btree_set = btree_set.into_iter().filter(|x| x % 2 == 0).collect(); | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: consider calling `.retain()` instead: `btree_set.retain(|x| x % 2 == 0)` error: this expression can be written more simply using `.retain()` - --> $DIR/use_retain.rs:93:5 + --> $DIR/use_retain.rs:103:5 | LL | hash_map = hash_map.into_iter().filter(|(k, _)| k % 2 == 0).collect(); | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: consider calling `.retain()` instead: `hash_map.retain(|k, _| k % 2 == 0)` error: this expression can be written more simply using `.retain()` - --> $DIR/use_retain.rs:94:5 + --> $DIR/use_retain.rs:104:5 | LL | hash_map = hash_map.into_iter().filter(|(_, v)| v % 2 == 0).collect(); | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: consider calling `.retain()` instead: `hash_map.retain(|_, &mut v| v % 2 == 0)` error: this expression can be written more simply using `.retain()` - --> $DIR/use_retain.rs:95:5 + --> $DIR/use_retain.rs:105:5 | LL | / hash_map = hash_map LL | | .into_iter() @@ -55,46 +61,64 @@ LL | | .collect(); | |__________________^ help: consider calling `.retain()` instead: `hash_map.retain(|k, &mut v| (k % 2 == 0) && (v % 2 == 0))` error: this expression can be written more simply using `.retain()` - --> $DIR/use_retain.rs:116:5 + --> $DIR/use_retain.rs:126:5 | LL | hash_set = hash_set.into_iter().filter(|x| x % 2 == 0).collect(); | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: consider calling `.retain()` instead: `hash_set.retain(|x| x % 2 == 0)` error: this expression can be written more simply using `.retain()` - --> $DIR/use_retain.rs:117:5 + --> $DIR/use_retain.rs:127:5 | LL | hash_set = hash_set.iter().filter(|&x| x % 2 == 0).copied().collect(); | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: consider calling `.retain()` instead: `hash_set.retain(|x| x % 2 == 0)` error: this expression can be written more simply using `.retain()` - --> $DIR/use_retain.rs:139:5 + --> $DIR/use_retain.rs:128:5 + | +LL | hash_set = hash_set.iter().filter(|&x| x % 2 == 0).cloned().collect(); + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: consider calling `.retain()` instead: `hash_set.retain(|x| x % 2 == 0)` + +error: this expression can be written more simply using `.retain()` + --> $DIR/use_retain.rs:157:5 | LL | s = s.chars().filter(|&c| c != 'o').to_owned().collect(); | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: consider calling `.retain()` instead: `s.retain(|c| c != 'o')` error: this expression can be written more simply using `.retain()` - --> $DIR/use_retain.rs:151:5 + --> $DIR/use_retain.rs:169:5 | LL | vec = vec.iter().filter(|&x| x % 2 == 0).copied().collect(); | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: consider calling `.retain()` instead: `vec.retain(|x| x % 2 == 0)` error: this expression can be written more simply using `.retain()` - --> $DIR/use_retain.rs:152:5 + --> $DIR/use_retain.rs:170:5 + | +LL | vec = vec.iter().filter(|&x| x % 2 == 0).cloned().collect(); + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: consider calling `.retain()` instead: `vec.retain(|x| x % 2 == 0)` + +error: this expression can be written more simply using `.retain()` + --> $DIR/use_retain.rs:171:5 | LL | vec = vec.into_iter().filter(|x| x % 2 == 0).collect(); | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: consider calling `.retain()` instead: `vec.retain(|x| x % 2 == 0)` error: this expression can be written more simply using `.retain()` - --> $DIR/use_retain.rs:172:5 + --> $DIR/use_retain.rs:193:5 | LL | vec_deque = vec_deque.iter().filter(|&x| x % 2 == 0).copied().collect(); | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: consider calling `.retain()` instead: `vec_deque.retain(|x| x % 2 == 0)` error: this expression can be written more simply using `.retain()` - --> $DIR/use_retain.rs:173:5 + --> $DIR/use_retain.rs:194:5 + | +LL | vec_deque = vec_deque.iter().filter(|&x| x % 2 == 0).cloned().collect(); + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: consider calling `.retain()` instead: `vec_deque.retain(|x| x % 2 == 0)` + +error: this expression can be written more simply using `.retain()` + --> $DIR/use_retain.rs:195:5 | LL | vec_deque = vec_deque.into_iter().filter(|x| x % 2 == 0).collect(); | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: consider calling `.retain()` instead: `vec_deque.retain(|x| x % 2 == 0)` -error: aborting due to 15 previous errors +error: aborting due to 19 previous errors