我正在尝试将成员函数的主体作为宏参数传递。是否可以更改下面的代码以使其工作?
macro_rules! iterator{
($ty:ty, $ident:ident; $($state_ident:ident: $state_ty:ty), *; $next:block) => (
struct $ident { // ^ the parameter
$($state_ident: $state_ty), *
}
impl Iterator for $ident {
type Item = $ty;
fn next(&mut self) -> Option<$ty> {
$next // <- cannot refer to 'self' parameter in this block
}
}
);
}
iterator!(i32, TestIterator; index: i32; {
let value = Some(self.index);
self.index += 1;
value
});
编译器错误:
error[E0424]: expected value, found module `self`
--> src/main.rs:18:22
|
18 | let value = Some(self.index);
| ^^^^ `self` value is only available in methods with `self` parameter
error[E0424]: expected value, found module `self`
--> src/main.rs:19:5
|
19 | self.index += 1;
| ^^^^ `self` value is only available in methods with `self` parameter
最佳答案
一个解决方案是接受闭包而不是 block :
macro_rules! iterator{
($ty:ty, $ident:ident; $($state_ident:ident: $state_ty:ty),*; $next:expr) => (
struct $ident {
$($state_ident: $state_ty), *
}
impl Iterator for $ident {
type Item = $ty;
fn next(&mut self) -> Option<$ty> {
$next(self)
}
}
);
}
iterator!(i32, TestIterator; index: i32; |me: &mut TestIterator| {
let value = Some(me.index);
me.index += 1;
value
});
fn main() {}
这需要明确地将 self
传递给闭包。您不能在闭包中使用标识符 self
,因为 self
只允许在函数的参数列表中声明。
您还需要指定闭包参数的类型,这是定义为变量并稍后使用而不是立即使用的闭包的限制。
关于rust - 将成员函数体作为宏参数传递,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/28953262/