What does it mean to instantiate a Rust generic with an underscore?

It’s a placeholder. In this context, it means that there isn’t enough information for the compiler to infer a type.

You can use this in your code to make the compiler infer the type for you. For example:

pub fn main() {
    let letters: Vec<_> = vec!["a", "b", "c"]; // Vec<&str>
}

This is particularly handy because in many cases you can avoid using the “turbofish operator”:

fn main() {
    let bar = [1, 2, 3];
    let foos = bar.iter()
                  .map(|x| format!("{}", x))
                  .collect::<Vec<String>>(); // <-- the turbofish
}

vs

fn main() {
    let bar = [1, 2, 3];
    let foos: Vec<_> = bar // <-- specify a type and use '_' to make the compiler
                           //     figure the element type out
            .iter()
            .map(|x| format!("{}", x))
            .collect(); // <-- no more turbofish
}

Leave a Comment