如何有效地逐行迭代`Vec<Vec<T>`? [英] How do I efficiently iterate through a `Vec&lt;Vec&lt;T&gt;&gt;` row by row?

查看:59
本文介绍了如何有效地逐行迭代`Vec<Vec<T>`?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在编写一个库,它使用 Vec> 类型以列优先顺序存储数据(每个内部 Vec 代表一列).用户可以创建具有任何行和列长度的 Vec,但所有列都被限制为相同的长度.

I am writing a library which employs a Vec<Vec<T>> type to store data in column-major order (each inner Vec represents a column). The user can create a Vec<Vec<T>> with any row and column length but all columns are constrained to be the same length.

有时我需要按行高效地遍历 Vec>.我不想更改数组类型,因为大多数时候我需要按列向量"(一次一个完整的列向量)进行迭代.

I need to sometimes efficiently iterate through the Vec<Vec<T>> by row. I would like to not change the array type because most of the time I need to iterate "by column vector" (one full column vector at a time).

除非我遗漏了什么,否则 Iterator::zip 不是一个选项,因为我事先不知道列向量的数量.Itertools::izipItertools::multizip 也不可行.

Unless I am missing something, Iterator::zip is not an option because I do not know the number of column vectors in advance. Itertools::izip and Itertools::multizip are also not viable.

这是我的示例代码:

let array = vec![vec![1, 2, 3], vec![4, 5, 6], vec![7, 8, 9]];
let mut iterators: Vec<_> = array.iter().map(|x| x.iter()).collect();
for _ in 0..array[0].len() {
    let values: Vec<_> = iterators.iter_mut().map(|x| x.next().unwrap()).collect();
    dbg!(values);
}

我应该在开始迭代之前定义一个可变的 values 向量以避免在每个周期进行分配,还是编译器会处理这种优化?自己找到最简单的方法是什么?

Should I define a mutable values vector before starting the iterations to avoid allocations at each cycle, or will the compiler take care of this optimization anyway? What is the easiest method to find it myself?

是否有更有效/惯用的解决方案?

Are there more efficient / idiomatic solutions?

推荐答案

一旦我有了迭代器向量,我该如何将其转换为向量迭代器?

有两种方法可以创建迭代器:使用现有的迭代器适配器或实现自定义迭代器.

Once I have a vector of iterators, how can I convert it to an iterator of vectors?

There are two ways to create an Iterator: to use an existing iterator adapter or to implement a custom Iterator.

让我们采用第二种方法并定义一个采用迭代器向量的自定义迭代器类型:

Let's take the second approach and define a custom Iterator type that takes a vector of iterators:

struct DynamicZip<I>
where I: Iterator {
    iterators: Vec<I>
}

让我们提供一个迭代器实现:

and let's provide an Iterator implementation:

impl<I, T> Iterator for DynamicZip<I>
where I: Iterator<Item = T> {
    type Item = Vec<T>;
    fn next(&mut self) -> Option<Self::Item> {
        let output: Option<Vec<T>> = self.iterators.iter_mut().map(|iter| iter.next()).collect()
        output
    }
}

我们就完成了!

fn main() {
    let array = vec![vec![1, 2, 3], vec![4, 5, 6], vec![7, 8, 9]];
    let iterators: Vec<_> = array.into_iter().map(|v| v.into_iter()).collect();
    let dz = DynamicZip { iterators: iterators };
    // use the Iterator type we just defined
    for column in dz {
        println!("{:?}", column)
    }
}

将产生输出

[1, 4, 7]
[2, 5, 8]
[3, 6, 9]

这篇关于如何有效地逐行迭代`Vec<Vec<T>`?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆