I have a struct:
pub struct SomeCollection<'a> {
items: Vec<&'a SomeValue>,
name_mapping: HashMap<&'a str, usize>,
index_mapping: HashMap<&'a str, usize>
}
impl<'a> Index for SomeCollection<'a> {
type Output = Option<&'a SomeValue>;
fn index(&self, value_name: &str) -> &Self::Output {
match self.name_mapping.get(value_name) {
Some(index) => &self.items.get(index),
None => match self.index_mapping.get(value_name) {
Some(index) => &self.items.get(index),
None => &None
}
}
}
}
When I try compiling this code I get the following error:
error[E0277]: the trait bound `&usize: std::slice::SliceIndex<[&SomeValue]>` is not satisfied
--> src\some_collection.rs:49:48
|
49 | Some(index) => &self.items.get(index),
| ^^^ slice indices are of
type `usize` or ranges of `usize`
|
= help: the trait `std::slice::SliceIndex<[&SomeValue]>` is not implemented for `&usize`
Rust seems to be telling me that I can't index into a vector with index
, which is a usize
. I'm not sure why I need to implement this trait as it should be implemented for the default vector already. Can anyone enlighten me as to the real reason I'm getting this error? There may be other errors in this code that haven't surfaced yet so please bear that in mind when answering.
Rust seems to be telling me that I can't index into a vector with
index
, which is ausize
.
No, the compiler is telling you that you can't index a vector with an &usize
.
the trait `std::slice::SliceIndex<[&SomeValue]>` is not implemented for `&usize`
Simply using *index
instead will fix this particular problem. However, your code has other problems as well:
Index
trait needs a type parameter, eg &str
in this case. index()
method can generally only return a reference to data stored in the data structure you are indexing. Your code creates a temporary Option
, which is not stored in the original data, and then tries to return a reference to that. If this is what you want to do, you need to define your own method (or trait) that returns the Option
by value instead. Maybe the compiler error is hard to understand, but at least it is accurate. It tells you, that index
is a reference &usize
however a Vec
can only be indexed with the value usize
. So all you have to do is dereference index
.
Moreover, usually indexing panic
s if the key/index could not be found. (That's why the standard library offers the Vec::get
, and HashMap::get
as separate methods alongside indexing, which do not panic
but return None
if the given key/index not in the collection.)
impl<'a> Index<&str> for SomeCollection<'a> {
type Output = &'a SomeValue;
fn index(&self, value_name: &str) -> &Self::Output {
match self.name_mapping.get(value_name) {
Some(index) => &self.items[*index],
None => match self.index_mapping.get(value_name) {
Some(index) => &self.items[*index],
None => panic!("Missing key: {:?}", value_name),
}
}
}
}
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.