Compiler could suggest an Option type if conditional returns "()" instead of value

I'm playing around with Rust and noticed the compiler makes great suggestions. I think I hit a pattern that could be added. I wasn't sure if the issues were the right place to go because I'm only writing my hello worlds and fibonacci functions with the language, so I thought maybe this forum could be the right place to post about it.

Consider the following function:

fn fib1(n: u64) -> u64 {
    if n <= 2 { 1 }
    else if n >  2 { fib1(n - 1) + fib1(n - 2) }
    else           { }
}

The compiler will complain about the last else clause returning (). Encountering such a pattern I thought the compiler could suggest the use of an Option type, to arrive at something like:

fn fib1(n: u64) -> Option<u64> {
    if n <= 2 { Some(1) }
    else {
        let f1 = fib1(n - 1);
        let f2 = fib1(n - 2);
        match [f1, f2] {
            [Some(r1), Some(r2)] => Some(r1 + r2),
            [_,        _]        => None
        }
    }
}

Also, fiddling with the above, I encountered an compiler panic and the compiler asked me to report a bug, but not being familiar with the repo/compiler, I refrained. The code is:

fn fib1(n: u64) -> Option<u64> {
    if n <= 2 { Some(1) }
    else {
        if let Some(f1) = fib1(n - 1) &&
           let Some(f2) = fib1(n - 2) {
            Some(f1 + f2)
        } else {
            None
        }
    }
}

I ran it on the playground about 10 minutes ago.

The suggestion to use Option might be tricky. Figuring out that that is what the user might have intended or needed with a high degree of confidence might not be consistently possible. rustc has a high bar to clear before suggesting code changes as leading people astray is worse than being too terse.

As for the ICE, this is a known issue that is already resolved in the next version of the compiler (due to a confusion on my part it wasn't backported in time for the current stable).

4 Likes

Thanks for the reply!