rust 使用IndexMut时,编译时无法知道类型为`[bool]`的值的大小

6yoyoihd  于 2023-08-05  发布在  其他
关注(0)|答案(2)|浏览(121)

我尝试使用Bitmap类作为bools的 Package 器。因此,我希望能够使用切片索引并分配给切片。我来自python背景,所以我习惯了事情只是工作。在python中,你基本上定义了indexlen,你就可以开始了。显然,生 rust 是更复杂的打字和所有权和大小。我真的很喜欢它,想知道它是如何工作的。请耐心等待我的不理解。我是一个菜鸟生 rust ,但不是编码,虽然我的大部分经验是与动态语言。
实际上,我希望这个结构体的行为像一个可迭代的,这是为了支持索引和切片等。我认为解决办法可能与大小有关,但我不能肯定。

struct Bitmap <const N: usize> {
    bools: [bool;N],
}

impl<const N: usize> Bitmap<N> {
    fn new(bools: [bool;N]) -> Self {
        Bitmap { bools }
    }
}

impl<Idx, const N:usize> std::ops::Index<Idx> for Bitmap<N>
where
    Idx: std::slice::SliceIndex<[bool]>,
{
    type Output = Idx::Output;

    fn index(&self, index: Idx) -> &Self::Output {
        &self.bools[index]
    }
}

impl<const N: usize> std::ops::IndexMut<usize> for Bitmap<N> 
{
    fn index_mut(&mut self, index: usize) -> &mut Self::Output {
        &mut self.bools[index]
    }
}

fn main() {
    let mut test = Bitmap::<6>::new([true, false, true, false, true, false]);
    //Indexing works
    println!("{:?}", test[0]); 
    //Index assignment works
    test[0] = false; 
    //slicing works
    println!("{:?}", &test[1..]); 
    
    //But does not work when you do it like this
    let slice = [2..5].as_slice();
    println!("{:?}", &test[slice])
    //error[E0277]: the type `[bool]` cannot be indexed by `&[std::ops::Range<{integer}>]`
    
    //Slice assign does not work
    //test[0..2] = [false, true]; 
    //error[E0277]: the size for values of type `[bool]` cannot be known at compilation time
}

字符串
我尝试将impl<const N: usize> std::ops::IndexMut<usize> for Bitmap<N>的签名更改为类似于Index实现的签名,但出现错误。然后我尝试了一堆随机的东西。没有一个成功的。

ssm49v7z

ssm49v7z1#

你有没有试过从一个范围内得到一个切片,就像你在以前的尝试中所做的那样?

let slice = &test[2..5];
println!("{:?}", slice);

字符串
现在,同样的方法,但从一个范围

let range = 2..5; 
let slice = &test[range];
println!("{:?}", slice);

z0qdvdin

z0qdvdin2#

考虑一下这个:

let slice = [2..5].as_slice();
    println!("{:?}", &test[slice]);

字符串
第一行创建一个数组,初始化为值2,3,4,5,然后创建整个数组的一个切片,并将该值绑定到变量slice
第二行尝试使用该数组索引test。然而,Rust没有提供任何方法来使用从范围(&[std::ops::Range<{integer}>])生成的值切片来索引布尔数组([bool])。就这一点而言,它没有提供任何使用任何东西的切片来索引数组的方法。
你可以做的是一开始就不把range转换成数组:

let range = 2..5;                  // Variable contains range from 2..5
    println!("{:?}", &test[range]);    // Index using range


你可能会问为什么Rust不提供一种使用任意索引数组来索引数组的方法。对于您的示例情况,这似乎足够简单,但如果索引不相交(例如,[2,7,8])呢?阵列是连续的存储器块;切片是对存储器的连续块的引用;范围索引操作返回一个引用底层数组的切片,但是如果索引不相交,它会返回什么呢?

相关问题