簡體   English   中英

如何編寫一個值加倍的迭代器?

[英]How do I write a value doubling iterator?

我想從1的基本值開始,然后將每次迭代的2乘以我的基本值,直到定義的限制(例如數組的總長度)。

為此我是否必須實現一個特殊的迭代器? 或者我可以將其他迭代器方法(例如mapfilter組合在一起以實現相同的功能。 盡管我可以想象具體實現我的迭代器會更高效,但也會更加冗長。

您可以使用Iterator::scan

use std::iter;

fn main() {
    let items = iter::repeat(()).scan(1i32, |state, _| {
        let current_state = *state;
        *state = current_state * 2;
        Some(current_state)
    });

    println!("{:?}", items.take(10).collect::<Vec<_>>());
}

這具有一個小的狀態,該狀態從您的初始值( 1i32 )開始,並且每次都將狀態翻倍,並返回前一個狀態。


由於閉包捕獲了他們的環境,因此您可以不使用scan來執行此操作,盡管我希望迭代器包含它們所需的所有信息,所以我不太可能實際執行此操作:

let mut state = 1;
let items = iter::repeat(()).map(|_| {
    let v = state;
    state *= 2;
    v
});

而且總是有長形式:

struct Doubling {
    value: i32,
}

impl Doubling {
    fn new(value: i32) -> Self {
        Self { value }
    }
}

impl Iterator for Doubling {
    type Item = i32;

    fn next(&mut self) -> Option<Self::Item> {
        let val = self.value;
        self.value *= 2;
        Some(val)
    }
}

fn main() {
    let items = Doubling::new(1);
    println!("{:?}", items.take(10).collect::<Vec<_>>());
}

您可以執行以下操作:

fn main() {
    for i in (0..).map(|n| 2usize.pow(n)).take(10) { // take(10) so it stops
        println!("{}", i);
    }
}

輸出:

1
2
4
8
16
32
64
128
256
512

它非常有效,不需要為此實現自己的迭代器。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM