Анд*_*ких 11 implementation traits rust
#![feature(unboxed_closures)]
#![feature(fn_traits)]
struct foo;
impl std::ops::Add for foo {
type Output = foo;
fn add(self, x: foo) -> foo {
println!("Add for foo");
x
}
}
impl Fn for foo {
extern "rust-call" fn call(&self) -> Self {
println!("Call for Foo ");
self
}
}
fn main() {
let x = foo;
let y = foo;
x + y;
x();
}
Run Code Online (Sandbox Code Playgroud)
我实现了Add特性,但我不明白如何将结构作为函数调用.我收到错误:
error[E0243]: wrong number of type arguments: expected 1, found 0
--> src/main.rs:14:10
|
14 | impl Fn for foo {
| ^^ expected 1 type argument
Run Code Online (Sandbox Code Playgroud)
我是Rust的新手,无法找到如何让这件事发生的例子.
She*_*ter 15
完全阅读您正在实施的特征以了解如何实现它非常有用.的Fn*性状的定义为:
pub trait Fn<Args>: FnMut<Args> {
extern "rust-call" fn call(&self, args: Args) -> Self::Output;
}
Run Code Online (Sandbox Code Playgroud)
注意实现和定义之间的任何差异?我看到很多:
实现不提供值#[feature]!这就是编译器指向的内容.另请参见错误的类型参数:预期1但找到0
该实现没有实现supertrait Fn,它本身需要supertrait Args.FnMut就是将相关的类型 FnOnce声明.
实现忽略了定义具体类型FnOnce应该是什么.
Output特征返回时实现返回Output.
实现不接受第二个参数Self.该参数包含传入的任何参数.
另外,Rust使用的类型Self::Output不是call,所以它应该是PascalCase.
#![feature(unboxed_closures)]
#![feature(fn_traits)]
struct Foo;
impl Fn<()> for Foo {
extern "rust-call" fn call(&self, _args: ()) {
println!("Call (Fn) for Foo");
}
}
impl FnMut<()> for Foo {
extern "rust-call" fn call_mut(&mut self, _args: ()) {
println!("Call (FnMut) for Foo");
}
}
impl FnOnce<()> for Foo {
type Output = ();
extern "rust-call" fn call_once(self, _args: ()) {
println!("Call (FnOnce) for Foo");
}
}
fn main() {
let x = Foo;
x();
}
Run Code Online (Sandbox Code Playgroud)
通常情况下,只有一个特征的实现会在其中包含有趣的代码,而其他特征实现将委托给它:
extern "rust-call" fn call(&self, args: ()) {
println!("Foo called, took args: {:?}", args);
}
// ...
extern "rust-call" fn call_mut(&mut self, args: ()) {
self.call(args)
}
// ...
extern "rust-call" fn call_once(self, args: ()) {
self.call(args)
}
Run Code Online (Sandbox Code Playgroud)
通过实现 Deref,您可以模拟所需的行为。然后,您只需在参数周围使用括号并获取返回值,就像调用函数一样。
请参阅此线程:https ://users.rust-lang.org/t/callable-struct-on-stable/54689/6
相关部分(感谢crawdad):
fn main() {
let func: Functionish = make_func();
func();
}
fn make_func() -> Functionish {
Functionish {
f: Box::new(|| println!("printing")),
}
}
struct Functionish {
f: Box<dyn Fn()>,
}
impl std::ops::Deref for Functionish {
type Target = dyn Fn();
fn deref(&self) -> &Self::Target {
&self.f
}
}
Run Code Online (Sandbox Code Playgroud)
这是我自己的代码中的一个不完整的示例,它采用参数,一个是引用,一个是可变引用。就我而言,闭包存储在 Rc 内,这需要奇数行,&(*self.function_container)因为我需要先进入 Rc,然后才能获取对闭包的引用。
pub struct FeelFunction {
pub function_type: FunctionType,
name_container: RefCell<String>,
function_container: Rc<dyn Fn(&FeelValue, &mut NestedContext) -> FeelValue>
}
impl Deref for FeelFunction {
type Target = dyn Fn(&FeelValue, &mut NestedContext) -> FeelValue;
fn deref(&self) -> &Self::Target {
&(*self.function_container)
}
}
Run Code Online (Sandbox Code Playgroud)
| 归档时间: |
|
| 查看次数: |
1223 次 |
| 最近记录: |