如何将&[u8]转换为&[u8; 64]?

时间:2019-10-20 23:27:19

标签: rust type-conversion

我正在编写占用64字节块的代码,并且我想在类型级别上强制使用此大小:

i

但是,数据以切片fn f(buf: &[u8; 64]) { ... } 的形式进入。因此,我希望能够使用此子空间并将其转换为&[u8]。事实证明,以下转换有效:

&[u8; 64]

但是以下内容却没有:

let buf = (0..32).collect::<Vec<u8>>();
let z: &[u8; 32] = &(&buf[..]).try_into().unwrap();

从0到32(包括0和32)之间的差异,该转换有效,但对于32以上的尺寸无效。如何执行此let buf = (0..64).collect::<Vec<u8>>(); let z: &[u8; 64] = &(&buf[..]).try_into().unwrap(); -> &[u8]转换而无需手动执行数据复制? / p>

1 个答案:

答案 0 :(得分:1)

如果需要,可以将the code that Rust currently uses用于0-32号。

#[stable(feature = "try_from", since = "1.34.0")]
impl<'a, T, const N: usize> TryFrom<&'a [T]> for &'a [T; N]
where
    [T; N]: LengthAtMost32,
{
    type Error = TryFromSliceError;

    fn try_from(slice: &[T]) -> Result<&[T; N], TryFromSliceError> {
        if slice.len() == N {
            let ptr = slice.as_ptr() as *const [T; N];
            unsafe { Ok(&*ptr) }
        } else {
            Err(TryFromSliceError(()))
        }
    }
}

稳定常量泛型后,绑定的[T; N]: LengthAtMost32可能会被删除。在此之前,您可以实现自己的功能。晚上使用启用了常量泛型的函数,或者只是针对您的特定大小使用一个函数。

struct TryFromSliceError(());

fn slice_to_array_64<T>(slice: &[T]) -> Result<&[T; 64], TryFromSliceError> {
    if slice.len() == 64 {
        let ptr = slice.as_ptr() as *const [T; 64];
        unsafe {Ok(&*ptr)}
    } else {
        Err(TryFromSliceError(()))
    }
}

(playground)

相关问题