diff options
| -rw-r--r-- | clippy_lints/src/matches/nop_match.rs | 25 | ||||
| -rw-r--r-- | tests/ui/nop_match.fixed | 13 | ||||
| -rw-r--r-- | tests/ui/nop_match.rs | 15 | ||||
| -rw-r--r-- | tests/ui/nop_match.stderr | 23 |
4 files changed, 49 insertions, 27 deletions
diff --git a/clippy_lints/src/matches/nop_match.rs b/clippy_lints/src/matches/nop_match.rs index 74e7ca2d5fe..f13ee27df47 100644 --- a/clippy_lints/src/matches/nop_match.rs +++ b/clippy_lints/src/matches/nop_match.rs @@ -80,26 +80,29 @@ pub(crate) fn check(cx: &LateContext<'_>, ex: &Expr<'_>) { } fn check_if_let(cx: &LateContext<'_>, if_let: &higher::IfLet<'_>) -> bool { - if let Some(else_block) = if_let.if_else { + if let Some(if_else) = if_let.if_else { if !pat_same_as_expr(if_let.let_pat, peel_blocks_with_stmt(if_let.if_then)) { return false; } - let else_expr = peel_blocks_with_stmt(else_block); // Recurrsively check for each `else if let` phrase, - if let Some(ref nested_if_let) = higher::IfLet::hir(cx, else_expr) { + if let Some(ref nested_if_let) = higher::IfLet::hir(cx, if_else) { return check_if_let(cx, nested_if_let); } - let ret = strip_return(else_expr); - let let_expr_ty = cx.typeck_results().expr_ty(if_let.let_expr); - if is_type_diagnostic_item(cx, let_expr_ty, sym::Option) { - if let ExprKind::Path(ref qpath) = ret.kind { - return is_lang_ctor(cx, qpath, OptionNone) || eq_expr_value(cx, if_let.let_expr, ret); + + if matches!(if_else.kind, ExprKind::Block(..)) { + let else_expr = peel_blocks_with_stmt(if_else); + let ret = strip_return(else_expr); + let let_expr_ty = cx.typeck_results().expr_ty(if_let.let_expr); + if is_type_diagnostic_item(cx, let_expr_ty, sym::Option) { + if let ExprKind::Path(ref qpath) = ret.kind { + return is_lang_ctor(cx, qpath, OptionNone) || eq_expr_value(cx, if_let.let_expr, ret); + } + } else { + return eq_expr_value(cx, if_let.let_expr, ret); } - } else { - return eq_expr_value(cx, if_let.let_expr, ret); + return true; } - return true; } false } diff --git a/tests/ui/nop_match.fixed b/tests/ui/nop_match.fixed index c8c05b6f4a4..8875323a1bb 100644 --- a/tests/ui/nop_match.fixed +++ b/tests/ui/nop_match.fixed @@ -3,6 +3,7 @@ #![allow(clippy::manual_map)] #![allow(dead_code)] +#[derive(Clone, Copy)] enum Choice { A, B, @@ -60,8 +61,16 @@ fn if_let_result(x: Result<(), i32>) { let _: Result<(), i32> = if let Err(e) = Ok(1) { Err(e) } else { x }; } -fn custom_enum_a(x: Choice) -> Choice { - x +fn if_let_custom_enum(x: Choice) { + let _: Choice = x; + // Don't trigger + let _: Choice = if let Choice::A = x { + Choice::A + } else if true { + Choice::B + } else { + x + }; } fn main() {} diff --git a/tests/ui/nop_match.rs b/tests/ui/nop_match.rs index 978811e28d1..19469a86022 100644 --- a/tests/ui/nop_match.rs +++ b/tests/ui/nop_match.rs @@ -3,6 +3,7 @@ #![allow(clippy::manual_map)] #![allow(dead_code)] +#[derive(Clone, Copy)] enum Choice { A, B, @@ -79,8 +80,8 @@ fn if_let_result(x: Result<(), i32>) { let _: Result<(), i32> = if let Err(e) = Ok(1) { Err(e) } else { x }; } -fn custom_enum_a(x: Choice) -> Choice { - if let Choice::A = x { +fn if_let_custom_enum(x: Choice) { + let _: Choice = if let Choice::A = x { Choice::A } else if let Choice::B = x { Choice::B @@ -88,7 +89,15 @@ fn custom_enum_a(x: Choice) -> Choice { Choice::C } else { x - } + }; + // Don't trigger + let _: Choice = if let Choice::A = x { + Choice::A + } else if true { + Choice::B + } else { + x + }; } fn main() {} diff --git a/tests/ui/nop_match.stderr b/tests/ui/nop_match.stderr index 23a1d382a30..b7a1967bf5f 100644 --- a/tests/ui/nop_match.stderr +++ b/tests/ui/nop_match.stderr @@ -1,5 +1,5 @@ error: this match expression is unnecessary - --> $DIR/nop_match.rs:14:18 + --> $DIR/nop_match.rs:15:18 | LL | let _: i32 = match x { | __________________^ @@ -13,7 +13,7 @@ LL | | }; = note: `-D clippy::nop-match` implied by `-D warnings` error: this match expression is unnecessary - --> $DIR/nop_match.rs:23:21 + --> $DIR/nop_match.rs:24:21 | LL | let _: Choice = match se { | _____________________^ @@ -25,7 +25,7 @@ LL | | }; | |_____^ help: replace it with: `se` error: this match expression is unnecessary - --> $DIR/nop_match.rs:45:26 + --> $DIR/nop_match.rs:46:26 | LL | let _: Option<i32> = match x { | __________________________^ @@ -35,7 +35,7 @@ LL | | }; | |_____^ help: replace it with: `x` error: this match expression is unnecessary - --> $DIR/nop_match.rs:61:31 + --> $DIR/nop_match.rs:62:31 | LL | let _: Result<i32, i32> = match Ok(1) { | _______________________________^ @@ -45,7 +45,7 @@ LL | | }; | |_____^ help: replace it with: `Ok(1)` error: this match expression is unnecessary - --> $DIR/nop_match.rs:65:31 + --> $DIR/nop_match.rs:66:31 | LL | let _: Result<i32, i32> = match func_ret_err(0_i32) { | _______________________________^ @@ -55,33 +55,34 @@ LL | | }; | |_____^ help: replace it with: `func_ret_err(0_i32)` error: this if-let expression is unnecessary - --> $DIR/nop_match.rs:72:5 + --> $DIR/nop_match.rs:73:5 | LL | if let Some(a) = Some(1) { Some(a) } else { None } | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: replace it with: `Some(1)` error: this if-let expression is unnecessary - --> $DIR/nop_match.rs:76:30 + --> $DIR/nop_match.rs:77:30 | LL | let _: Result<(), i32> = if let Err(e) = x { Err(e) } else { x }; | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: replace it with: `x` error: this if-let expression is unnecessary - --> $DIR/nop_match.rs:77:30 + --> $DIR/nop_match.rs:78:30 | LL | let _: Result<(), i32> = if let Ok(val) = x { Ok(val) } else { x }; | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: replace it with: `x` error: this if-let expression is unnecessary - --> $DIR/nop_match.rs:83:5 + --> $DIR/nop_match.rs:84:21 | -LL | / if let Choice::A = x { +LL | let _: Choice = if let Choice::A = x { + | _____________________^ LL | | Choice::A LL | | } else if let Choice::B = x { LL | | Choice::B ... | LL | | x -LL | | } +LL | | }; | |_____^ help: replace it with: `x` error: aborting due to 9 previous errors |
