问题描述
我正在寻找类似于 slice::split_at_mut
的函数。让我们用签名将其命名为 split_at
pub fn split_at<T>(v: Vec<T>,mid: usize) -> (Vec<T>,Vec<T>)
这样
let v = vec![1,2,3,4];
let (first,second) = split_at(v,2);
assert_eq!(first,vec![1,2]);
assert_eq!(second,vec![3,4]);
该函数不应分配内存,只需将向量一分为二。您无需担心容量,因为结果向量不会被修改。
仅夜间使用的方法 Vec::into_raw_parts
看起来很有前途,但我在稳定的发布渠道上不允许使用此类方法。
解决方法
您的请求,正如措辞,用 Vec
是不可能的。 Vec
表示分配的内存的唯一所有权。当 Vec
超出范围时,该内存将被释放。
如果你能做到你所要求的,那么你要么
- 释放一段内存两次(起始内存)
- 解除分配一块未分配的内存(内存中间的某处)
这两种情况都是内存不安全,这正是 Rust 旨在防止的。
您可能来自带有垃圾收集器的编程语言,这也是解决相同问题的一种方法。
bytes crate 提供了一个引用计数的类向量类型,称为 Bytes
(或其他情况下的 BytesMut
):
use bytes::Bytes; // 1.0.1
fn main() {
let v = Bytes::from(vec![1,2,3,4]);
let (first,second) = v.split_at(2);
assert_eq!(first,vec![1,2]);
assert_eq!(second,vec![3,4]);
}
,
不完全是我想要的,但 split_off
已经足够接近了。
let mut vec = vec![1,3];
let vec2 = vec.split_off(1);
assert_eq!(vec,[1]);
assert_eq!(vec2,[2,3]);
回答我自己的问题
pub fn split_at<T>(mut v: Vec<T>,mid: usize) -> (Vec<T>,Vec<T>) {
let remainder = v.split_off(mid);
(v,remainder)
}