提问人:Test 提问时间:9/22/2022 最后编辑:HerohtarTest 更新时间:9/27/2022 访问量:51
临时值的正确函数类型
Correct Function Type for temporary value
问:
在函数内部调用的“回调”函数的正确函数类型是什么?
fn or_else(value: u32, f: ???) -> u32 {
if (value == 0) {
f()
} else {
value
}
}
用法示例:
or_else(0, || { 3 })
我使用时生锈是怎么回事?f: &dyn FnOnce() -> u32
错误:
cannot move a value of type dyn FnOnce() -> u32: the size of dyn FnOnce() -> u32 cannot be statically determinedrustcE0161
cannot move out of `*f` which is behind a shared reference
move occurs because `*f` has type `dyn FnOnce() -> u32`, which does not implement the `Copy` trait
我无法理解 E0161。
答:
3赞
Kevin Reid
9/22/2022
#1
在本例中,接受函数的最一般方法是使用以下任一语法使函数泛型:
fn or_else(value: u32, f: impl FnOnce() -> u32) -> u32 {
fn or_else<F: FnOnce() -> u32>(value: u32, f: F) -> u32 {
这就是说:可以是调用方愿意提供的任何类型,只要该类型实现(是一个可以调用一次的函数)。f
FnOnce
当我使用 f: 时,生锈生气是什么?
&dyn FnOnce() -> u32
FnOnce
以它只能调用一次的想法命名,但它的实际意思是通过调用函数值来消耗(移动)。因此,一旦你调用了这个函数,你就不再拥有它了。
但是,如果你有,那么你就不能移动这个值,因为你不拥有它。因此,不可能通过引用来调用。(同样,a 需要可变引用,并且不能使用不可变引用来调用。&F
F
FnOnce
FnMut
所以,这个类型是无用的——它可以存在,但它永远不能被调用。如果你想使用(这可能是一个合理的选择),那么你必须使用 or .&dyn FnOnce
dyn
&dyn Fn
&mut dyn FnMut
但是,对于接受回调的通用函数,通常最好使用泛型而不是 .这是因为:dyn
- 它允许你接受,最一般的功能特征
FnOnce
- 它允许通过值或引用传递函数,如果对于特定函数来说是可能的,因为对 / 函数的引用也实现 / 本身
Fn
FnMut
Fn
FnMut
- 它允许编译器内联回调函数,以便代码可以作为一个整体进行优化
上一个:如何在 rust 中触发异步回调
下一个:保留在闭包中使用的值以备后用
评论
FnOnce
FnMut
&mut dyn FnMut()
impl FnOnce()