Returning a simpler Iterator interface instead of a map in Rust

I would like to write the following:

fn fibs() -> std::iter::Iterator<int> { return std::iter::iterate((1i, 1i), |(a, b)| { (b, a + b) }).map(|(a, _)| a) } 

But if I do this, I get this error:

 error: explicit lifetime bound required fn fibs() -> std::iter::Iterator<int> { ^^^^^^^^^^^^^^^^^^^^^^^^ 

If instead I write out the full interface, it compiles:

 fn fibs() -> std::iter::Map<'static, (int, int), int, std::iter::Iterate<'static, (int, int)>> { return std::iter::iterate((1i, 1i), |(a, b)| { (b, a + b) }).map(|(a, _)| a) } 

Is there a way to bring back a simpler interface?

+6
source share
2 answers

There is currently no way to return an abstract type, such as Iterator<T> , just as you cannot assign it as the type of a variable ( let x: Iterator<uint>; do not compile for the same reasons).

This one has been discussed and is certainly desirable; when this is done, it will probably be in the form of fn fibs() -> impl Iterator<uint> , but you cannot do it.

+6
source

as @ChrisMorgan said, until you can return an abstract type. If you are creating a public API and want to avoid being overly dependent on a particular iterate and map implementation, you can encapsulate the return type in your own structure (which is more or less what the collections in the std library themselves do).

Sort of:

 // updated to rustc 0.13.0-nightly (2015-01-02) use std::iter::{Map, iterate, Unfold}; type Fibs = Map<(int, int), int, Unfold<(int, int), (fn((int, int)) -> (int, int), Option<(int, int)>, bool), fn(&mut (fn((int, int)) -> (int, int), Option<(int, int)>, bool)) -> Option<(int, int)>>, fn((int, int)) -> int>; struct Fibs2 { iter: Fibs, } impl Fibs2 { fn iter() -> Fibs2 { fn inner((a, b): (int, int)) -> (int, int) { (b, a + b) } let in_fn = inner as fn((int, int)) -> (int, int); fn first((a, _): (int, int)) -> int { a } let p_first = first as fn((int, int)) -> int; Fibs2{ iter: iterate((1i, 1i), in_fn).map(p_first) } } } impl Iterator<int> for Fibs2 { fn next(&mut self) -> Option<int> { self.iter.next() } } fn main() { for fib_n in Fibs2::iter().take(10) { println!("{}", fib_n); } } 
+1
source

Source: https://habr.com/ru/post/976645/


All Articles