Expected `i32`, found `&{integer}`

I've been experimenting with iterators and I would like to know what is wrong with this piede of code. I wanted to make a program which separates adjacent elements with 1+n separator, so I have created a closure for that. It returns i32 type, but the compiler thinks it returns &{integer} type when I try to use it. Is there a way to fix that?

let mut src = [1,2,3,4,5].iter();
let mut x = 0;
let mut closure =move || ->  i32{
    x+=1;
    return x;
};
let mut n = 0;
//println!("{:?}",closure(&mut n));
let result = src.intersperse_with(closure);

The error I get:

let result = src.intersperse_with(closure);
| ^^^^^^^^^^^^^^^^ expected i32, found &{integer}

[array].iter() returns slice::Iter, which iterates over references to the contents of the array. You're wanting to iterate over the actual contents of the array. There are a few ways to fix it. The simplest for now is probably:

let src = [1, 2, 3, 4, 5].iter().copied();

This will copy the integers out from behind their references. You can also do:

let src = std::array::IntoIter::new([1, 2, 3, 4, 5]);

This will consume the array and give you an iterator over the integers within. (You won't be able to use the array afterwards, since it gets consumed.)

Normally with collections (like Vec), you can call into_iter() instead of iter() to consume the collection and return the contents within. However, array is a special case; this only recently became possible due to const generics. In edition 2021 (but not 2018), this will also work:

// Same as `array::IntoIter::new(...)` in edition 2021
let src = [1, 2, 3, 4, 5].into_iter();

Note: We're still on edition 2018.

Try them here.

3 Likes

You can also do <_>::into_iter([1, 2, 3, 4, 5]) and that works in edition 2018 while avoiding the to-be-deprecated array::IntoIter::new function.

By the way, {integer} means "an as-yet-unknown integer type", and is created by an integer literal. In the absence of any other indication that the integer should be a specific integer type, Rust will eventually default to i32. So when you see {integer} in error messages, that means "whatever integer type you're using, but Rust hasn't got to the stage of actually figuring out what it is yet".

8 Likes

Wow, this really worked out! Thanks you a lot!

Thanks you!

This topic was automatically closed 90 days after the last reply. We invite you to open a new topic if you have further questions or comments.