Skip to content

[return_and_then] False Positive on Nightly #15111

Open
@JP-Ellis

Description

@JP-Ellis

Summary

I have recently run into a number of false positives of the return_and_then on the nightly build. Situations where I have seen this:

  • In (some) if let bindings
    if let Some(val) = opt.and_then(...)
    
  • In struct creations
    SomeStruct { val: opt.and_then(...) }
    

Lint Name

return_and_then

Reproducer

I tried this code:

#![allow(dead_code)]
#![warn(clippy::return_and_then)]

#[derive(Debug)]
struct EvenOdd {
    even: Option<u32>,
    odd: Option<u32>,
}

impl EvenOdd {
    fn new(i: Option<u32>) -> Self {
        Self {
            even: i.and_then(|i| if i%2 == 0 { Some(i) } else { None }),
            odd: i.and_then(|i| if i%2 == 0 { None } else { Some(i) }),
        }
    }
}

fn main() {
    let even_odd = EvenOdd::new(Some(2));
    dbg!(even_odd);
}

I saw this happen:

    Checking playground v0.0.1 (/playground)
warning: use the `?` operator instead of an `and_then` call
  --> src/main.rs:13:19
   |
13 |             even: i.and_then(|i| if i%2 == 0 { Some(i) } else { None }),
   |                   ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
   |
   = help: for further information visit https://rust-lang.github.io/rust-clippy/master/index.html#return_and_then
note: the lint level is defined here
  --> src/main.rs:2:9
   |
2  | #![warn(clippy::return_and_then)]
   |         ^^^^^^^^^^^^^^^^^^^^^^^
help: try
   |
13 ~             even: let i = i?;
14 ~             if i%2 == 0 { Some(i) } else { None },
   |

warning: use the `?` operator instead of an `and_then` call
  --> src/main.rs:14:18
   |
14 |             odd: i.and_then(|i| if i%2 == 0 { None } else { Some(i) }),
   |                  ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
   |
   = help: for further information visit https://rust-lang.github.io/rust-clippy/master/index.html#return_and_then
help: try
   |
14 ~             odd: let i = i?;
15 ~             if i%2 == 0 { None } else { Some(i) },
   |

warning: `playground` (bin "playground") generated 2 warnings (run `cargo clippy --fix --bin "playground"` to apply 2 suggestions)
    Finished `dev` profile [unoptimized + debuginfo] target(s) in 0.60s

I expected to see this happen:

  • No error message

Playground link

Version

rustc 1.89.0-nightly (d4e1159b8 2025-06-21)
binary: rustc
commit-hash: d4e1159b8c97478778b09a4cc1c7adce5653b8bf
commit-date: 2025-06-21
host: aarch64-apple-darwin
release: 1.89.0-nightly
LLVM version: 20.1.7

Additional Labels

No response

Metadata

Metadata

Assignees

Labels

C-bugCategory: Clippy is not doing the correct thingI-false-positiveIssue: The lint was triggered on code it shouldn't have

Type

No type

Projects

No projects

Milestone

No milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions