我正在尝试从结构中提取函数。原始(工作)是:
\b(is|small)\b
pub fn f(&self, id: Id) -> &[Foo] {
self.foos.get(&id).map_or(&[], |foos| &**foos)
}
是self.foos
提取后我有
HashMap<Id, Vec<Foo>, BuildHasherDefault<FnvHasher>>
产生的错误是
fn f<'a>(foos: HashMap<Id, Vec<Foo>, BuildHasherDefault<FnvHasher>>, id: Id) -> &'a [Foo] {
&foos.get(&id).map_or(&[], |xs| &**xs);
}
我想我需要提供一个类型提示。这是正确的吗?如果是这样,我如何在调用error: mismatched types:
expected `&[_; 0]`,
found `&[foo::Foo]`
(expected array of 0 elements,
found slice) [E0308]
U
的类型
答案 0 :(得分:7)
您遇到的错误会隐藏代码的实际问题。在这种情况下,通过更明确,编译器可以进一步提供与解决问题更相关的其他错误。
首先,让我们通过将&[]
更改为&[][..]
将数组显式转换为切片来消除类型不匹配。
fn f<'a>(foos: HashMap<Id, Vec<Foo>, BuildHasherDefault<FnvHasher>>, id: Id) -> &'a [Foo] {
&foos.get(&id).map_or(&[][..], |xs| &**xs);
}
我们现在收到此错误:
error: not all control paths return a value [--explain E0269]
--> <anon>:16:1
|>
16 |> fn f<'a>(foos: HashMap<Id, Vec<Foo>, BuildHasherDefault<FnvHasher>>, id: Id) -> &'a [Foo] {
|> ^
啊哈哈!函数末尾有一个分号,不应该在那里。我们将其删除。
fn f<'a>(foos: HashMap<Id, Vec<Foo>, BuildHasherDefault<FnvHasher>>, id: Id) -> &'a [Foo] {
&foos.get(&id).map_or(&[][..], |xs| &**xs)
}
嗯,还是没有编译:
error: `foos` does not live long enough
--> <anon>:17:6
|>
17 |> &foos.get(&id).map_or(&[][..], |xs| &**xs)
|> ^^^^
note: reference must be valid for the lifetime 'a as defined on the block at 16:90...
--> <anon>:16:91
|>
16 |> fn f<'a>(foos: HashMap<Id, Vec<Foo>, BuildHasherDefault<FnvHasher>>, id: Id) -> &'a [Foo] {
|> ^
note: ...but borrowed value is only valid for the scope of function body at 16:90
--> <anon>:16:91
|>
16 |> fn f<'a>(foos: HashMap<Id, Vec<Foo>, BuildHasherDefault<FnvHasher>>, id: Id) -> &'a [Foo] {
|> ^
基本上,错误是您尝试将借用的指针返回到HashMap
,该f
将在HashMap
调用结束时被销毁(因为HashMap
}按值传递)。您需要通过引用传递[..]
。我们现在可以摆脱不必要的fn f(foos: &HashMap<Id, Vec<Foo>, BuildHasherDefault<FnvHasher>>, id: Id) -> &[Foo] {
foos.get(&id).map_or(&[], |xs| &**xs)
}
因为它编译了!
list_of_attributes = ["a1", "a2", "a3", "a4"]
user_selections = ["a2", "a4"]