Можно ли объединить итераторы? - PullRequest
1 голос
/ 11 апреля 2019
let vec = iter::repeat("don't satisfy condition 1") // iterator such as next() always "don't " satisfy condition 1"
    .take_while(|_| {
        satisfycondition1.satisfy() // true is condition 1 is satisfied else false
    })
    .collect();

Этот код создает вектор из n элементов с n, равным количеству случаев, когда условие 1 не выполняется.

Я хотел бы сейчас создать вектор из n + m элементов с n, равным количеству раз, когда условие 1 не соблюдается, и m число раз, когда условие 2 не соблюдается.

Код должен выглядеть примерно так:

let vec = iter::repeat("dont't satisfy condition 1")
    .take_while(|_| {
        satisfycondition1.satisfy() 
    })
    .union(
        iter::repeat("has satisfed condition 1 but not 2 yet")
        .take_while(|_| {
            satisfycondition2.satisfy() 
        })
    )
    .collect();

Я знаю, что мог бы создать два вектора и затем объединить их, но это менее эффективно.

Вы можете использовать этот код, чтобы понять, что повторяется:

use  std::iter;

fn main() {
    let mut c = 0;
    let z: Vec<_> = iter::repeat("dont't satisfy condition 1")
        .take_while(|_| {
            c = c + 1;
            let rep = if c < 5 { true } else { false };
            rep
        })
        .collect();
    println!("------{:?}", z);
}

1 Ответ

5 голосов
/ 11 апреля 2019

Кажется, что std::iter::chain - это то, что вы ищете.

use std::iter;

fn main() {
    let mut c = 0;
    let mut d = 5;
    let z: Vec<_> = iter::repeat("don't satisfy condition 1")
        .take_while(|_| {
            c = c + 1;
            let rep = if c < 5 { true } else { false };
            rep
            // this block can be simplified to
            // c += 1;
            // c < 5
            // Clippy warns about this
        })
        .chain(
            iter::repeat("satisfy condition 1 but not 2").take_while(|_| {
                d -= 1;
                d > 2
            }),
        )
        .collect();
    println!("------{:?}", z);
}

(ссылка на игровую площадку)

Я могуНе комментируйте семантику вашего кода.Если вы пытаетесь увидеть, какие элементы итератора «удовлетворяют условию 1, но не 2», это будет не так, как вы это делаете.Чтобы достичь этого, вы должны использовать std::iter::filter дважды (один раз с условием 1 и один без условия 2).

...