【问题标题】:How to implement the `Index` trait for a simple struct?如何为简单结构实现“索引”特征?
【发布时间】:2021-11-13 10:08:11
【问题描述】:

我正在尝试为一个简单的特征实现 Index 特征,并且我想将它与 usize 一起使用。我添加了SliceIndex<[T], Output = T>,所以我可以使用T 来索引slice 内的A。

use std::ops::Index;
use std::slice::SliceIndex;

struct A <'a, T>{
    slice: &'a [T]
}

impl<'a, T: Index<T, Output = T> + SliceIndex<[T], Output = T>> Index<T>
    for A<'a, T>
{
    type Output = T;

    #[inline(always)]
    fn index(&self, index: T) -> &Self::Output {
        self.slice.index(index)
    }
}

fn main() {
    let mut aa: Vec<u64> = vec![0; 10];
    let coefficient_iterable = A{slice: &aa};
    println!("{}", coefficient_iterable[1usize]);
}

https://play.rust-lang.org/?version=stable&mode=debug&edition=2021&gist=9564b39061cae3e19db14217c10b9d8a

但我明白了:

错误:

error[E0608]: cannot index into a value of type `A<'_, u64>`
  --> src/main.rs:22:20
   |
22 |     println!("{}", coefficient_iterable[1usize]);
   |                    ^^^^^^^^^^^^^^^^^^^^^^^^^^^^

For more information about this error, try `rustc --explain E0608`.
error: could not compile `playground` due to previous error

我不知道为什么,因为usize 实现了SliceIndex&lt;[T]&gt;。

【问题讨论】:

    标签: rust


    【解决方案1】:

    要求T 既是Index 又是SliceIndex 没有意义,因为Index 描述了可索引容器的行为,而SliceIndex 是一个界限,您可以设置一个通用索引类型来使它更灵活。

    您不想实现Index&lt;T&gt;,因为这里的T 是切片中项目的类型,而不是索引的类型。要使main 函数中的代码正常工作,您可以只实现Index&lt;usize&gt;,但通常实现Index&lt;Idx&gt;(其中Idx: SliceIndex)提供了更大的灵活性,因此您也可以使用范围。

    use std::ops::Index;
    use std::slice::SliceIndex;
    
    struct A<'a, T> {
        slice: &'a [T],
    }
    
    impl<'a, T, Idx> Index<Idx> for A<'a, T>
    where
        Idx: SliceIndex<[T], Output = T>,
    {
        type Output = T;
    
        #[inline(always)]
        fn index(&self, index: Idx) -> &Self::Output {
            self.slice.index(index)
        }
    }
    
    fn main() {
        let aa: Vec<u64> = vec![0; 10];
        let coefficient_iterable = A { slice: &aa };
        assert_eq!(coefficient_iterable[1], 0);
    }
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2017-01-04
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2015-08-07
      • 2021-11-14
      相关资源
      最近更新 更多