在Rust中有可能连接向量吗?如果有,有没有一种优雅的方法可以做到这一点?我有这样的东西:
let mut a = vec![1, 2, 3]; let b = vec![4, 5, 6]; for val in &b { a.push(val); }
有人知道更好的办法吗?
rkue9o1l1#
结构std::vec::Vec具有方法append():
std::vec::Vec
append()
fn append(&mut self, other: &mut Vec<T>)
将other的所有元素移动到Self中,other保留为空。在您的示例中,以下代码将通过mutatinga和b来连接两个向量:
other
Self
a
b
fn main() { let mut a = vec![1, 2, 3]; let mut b = vec![4, 5, 6]; a.append(&mut b); assert_eq!(a, [1, 2, 3, 4, 5, 6]); assert_eq!(b, []); }
或者,可以使用Extend::extend()将可以转换为迭代器(如Vec)的某个对象的所有元素附加到给定向量:
Extend::extend()
Vec
let mut a = vec![1, 2, 3]; let b = vec![4, 5, 6]; a.extend(b); assert_eq!(a, [1, 2, 3, 4, 5, 6]); // b is moved and can't be used anymore
注意向量b被移动而不是清空。如果你的向量包含实现Copy的元素,你可以传递一个对一个向量的不可变引用给extend()以避免移动。在这种情况下,向量b不变:
Copy
extend()
let mut a = vec![1, 2, 3]; let b = vec![4, 5, 6]; a.extend(&b); assert_eq!(a, [1, 2, 3, 4, 5, 6]); assert_eq!(b, [4, 5, 6]);
xe55xuns2#
我不能在一条线上完成。可以使用chain()在一行中完成此操作:
chain()
let c: Vec<i32> = a.into_iter().chain(b.into_iter()).collect(); // Consumed let c: Vec<&i32> = a.iter().chain(b.iter()).collect(); // Referenced let c: Vec<i32> = a.iter().cloned().chain(b.iter().cloned()).collect(); // Cloned let c: Vec<i32> = a.iter().copied().chain(b.iter().copied()).collect(); // Copied
有无数种方法。
ifmq2ha23#
在性能方面,slice::concat、append和extend是差不多的,如果你不需要立即得到结果,把它做成链式迭代器是最快的;如果你需要collect(),它是最慢的:
slice::concat
append
extend
collect()
#![feature(test)] extern crate test; use test::Bencher; #[bench] fn bench_concat___init__(b: &mut Bencher) { b.iter(|| { let mut x = vec![1i32; 100000]; let mut y = vec![2i32; 100000]; }); } #[bench] fn bench_concat_append(b: &mut Bencher) { b.iter(|| { let mut x = vec![1i32; 100000]; let mut y = vec![2i32; 100000]; x.append(&mut y) }); } #[bench] fn bench_concat_extend(b: &mut Bencher) { b.iter(|| { let mut x = vec![1i32; 100000]; let mut y = vec![2i32; 100000]; x.extend(y) }); } #[bench] fn bench_concat_concat(b: &mut Bencher) { b.iter(|| { let mut x = vec![1i32; 100000]; let mut y = vec![2i32; 100000]; [x, y].concat() }); } #[bench] fn bench_concat_iter_chain(b: &mut Bencher) { b.iter(|| { let mut x = vec![1i32; 100000]; let mut y = vec![2i32; 100000]; x.into_iter().chain(y.into_iter()) }); } #[bench] fn bench_concat_iter_chain_collect(b: &mut Bencher) { b.iter(|| { let mut x = vec![1i32; 100000]; let mut y = vec![2i32; 100000]; x.into_iter().chain(y.into_iter()).collect::<Vec<i32>>() }); }
running 6 tests test bench_concat___init__ ... bench: 27,261 ns/iter (+/- 3,129) test bench_concat_append ... bench: 52,820 ns/iter (+/- 9,243) test bench_concat_concat ... bench: 53,566 ns/iter (+/- 5,748) test bench_concat_extend ... bench: 53,920 ns/iter (+/- 7,329) test bench_concat_iter_chain ... bench: 26,901 ns/iter (+/- 1,306) test bench_concat_iter_chain_collect ... bench: 190,334 ns/iter (+/- 16,107)
fkaflof64#
我认为连接一个或多个向量的最佳方法是:
let first_number: Vec<usize> = Vec::from([0]); let final_number: Vec<usize> = Vec::from([3]); let middle_numbers: Vec<usize> = Vec::from([1,2]); let numbers = [input_layer, middle_layers, output_layer].concat();
xxb16uws5#
对Mattia Samiolo的answer进行了一些修复:
let first_number: Vec<usize> = Vec::from([0]); let final_number: Vec<usize> = Vec::from([3]); let middle_numbers: Vec<usize> = Vec::from([1, 2]); let numbers = [first_number, middle_numbers, final_number].concat(); println!("{:?}", numbers);
gtlvzcf86#
一种选择是使用extend方法,它允许你将一个向量的元素附加到另一个向量上,如下所示:
let mut a = vec![1, 2, 3]; let b = vec![4, 5, 6]; a.extend(b);
这将把B的元素附加到a的末尾,得到具有元素[1,2,3,4,5,6]的向量a。另一种方法是使用std::iter模块中的concat函数来连接两个向量,这个函数将两个向量作为参数,并返回一个新向量,这个新向量是两个输入向量的连接,如下所示:
use std::iter; let a = vec![1, 2, 3]; let b = vec![4, 5, 6]; let c = iter::concat(a, b);
这将创建具有元素[1,2,3,4,5,6]的新向量c。您也可以使用[..]运算符连接两个向量。此运算符允许您创建一个新向量,该向量是两个输入向量的连接。如下所示:
let a = vec![1, 2, 3]; let b = vec![4, 5, 6]; let c = [&a[..], &b[..]].concat();
这将创建具有元素[1,2,3,4,5,6]的新向量c。
6条答案
按热度按时间rkue9o1l1#
结构
std::vec::Vec
具有方法append()
:将
other
的所有元素移动到Self
中,other
保留为空。在您的示例中,以下代码将通过mutating
a
和b
来连接两个向量:或者,可以使用
Extend::extend()
将可以转换为迭代器(如Vec
)的某个对象的所有元素附加到给定向量:注意向量
b
被移动而不是清空。如果你的向量包含实现Copy
的元素,你可以传递一个对一个向量的不可变引用给extend()
以避免移动。在这种情况下,向量b
不变:xe55xuns2#
我不能在一条线上完成。
可以使用
chain()
在一行中完成此操作:有无数种方法。
ifmq2ha23#
在性能方面,
slice::concat
、append
和extend
是差不多的,如果你不需要立即得到结果,把它做成链式迭代器是最快的;如果你需要collect()
,它是最慢的:fkaflof64#
我认为连接一个或多个向量的最佳方法是:
xxb16uws5#
对Mattia Samiolo的answer进行了一些修复:
gtlvzcf86#
一种选择是使用extend方法,它允许你将一个向量的元素附加到另一个向量上,如下所示:
这将把B的元素附加到a的末尾,得到具有元素[1,2,3,4,5,6]的向量a。
另一种方法是使用std::iter模块中的concat函数来连接两个向量,这个函数将两个向量作为参数,并返回一个新向量,这个新向量是两个输入向量的连接,如下所示:
这将创建具有元素[1,2,3,4,5,6]的新向量c。
您也可以使用[..]运算符连接两个向量。此运算符允许您创建一个新向量,该向量是两个输入向量的连接。如下所示:
这将创建具有元素[1,2,3,4,5,6]的新向量c。