summaryrefslogtreecommitdiff
path: root/src/tools/clippy/clippy_lints/src/loops/mod.rs
diff options
context:
space:
mode:
Diffstat (limited to 'src/tools/clippy/clippy_lints/src/loops/mod.rs')
-rw-r--r--src/tools/clippy/clippy_lints/src/loops/mod.rs35
1 files changed, 34 insertions, 1 deletions
diff --git a/src/tools/clippy/clippy_lints/src/loops/mod.rs b/src/tools/clippy/clippy_lints/src/loops/mod.rs
index 610a0233eee..f83ad388a74 100644
--- a/src/tools/clippy/clippy_lints/src/loops/mod.rs
+++ b/src/tools/clippy/clippy_lints/src/loops/mod.rs
@@ -7,6 +7,7 @@ mod iter_next_loop;
mod manual_find;
mod manual_flatten;
mod manual_memcpy;
+mod manual_while_let_some;
mod missing_spin_loop;
mod mut_range_bound;
mod needless_range_loop;
@@ -575,6 +576,36 @@ declare_clippy_lint! {
"manual implementation of `Iterator::find`"
}
+declare_clippy_lint! {
+ /// ### What it does
+ /// Looks for loops that check for emptiness of a `Vec` in the condition and pop an element
+ /// in the body as a separate operation.
+ ///
+ /// ### Why is this bad?
+ /// Such loops can be written in a more idiomatic way by using a while-let loop and directly
+ /// pattern matching on the return value of `Vec::pop()`.
+ ///
+ /// ### Example
+ /// ```rust
+ /// let mut numbers = vec![1, 2, 3, 4, 5];
+ /// while !numbers.is_empty() {
+ /// let number = numbers.pop().unwrap();
+ /// // use `number`
+ /// }
+ /// ```
+ /// Use instead:
+ /// ```rust
+ /// let mut numbers = vec![1, 2, 3, 4, 5];
+ /// while let Some(number) = numbers.pop() {
+ /// // use `number`
+ /// }
+ /// ```
+ #[clippy::version = "1.70.0"]
+ pub MANUAL_WHILE_LET_SOME,
+ style,
+ "checking for emptiness of a `Vec` in the loop condition and popping an element in the body"
+}
+
declare_lint_pass!(Loops => [
MANUAL_MEMCPY,
MANUAL_FLATTEN,
@@ -594,6 +625,7 @@ declare_lint_pass!(Loops => [
SINGLE_ELEMENT_LOOP,
MISSING_SPIN_LOOP,
MANUAL_FIND,
+ MANUAL_WHILE_LET_SOME
]);
impl<'tcx> LateLintPass<'tcx> for Loops {
@@ -640,9 +672,10 @@ impl<'tcx> LateLintPass<'tcx> for Loops {
while_let_on_iterator::check(cx, expr);
- if let Some(higher::While { condition, body }) = higher::While::hir(expr) {
+ if let Some(higher::While { condition, body, span }) = higher::While::hir(expr) {
while_immutable_condition::check(cx, condition, body);
missing_spin_loop::check(cx, condition, body);
+ manual_while_let_some::check(cx, condition, body, span);
}
}
}