rust结构域由宏生成

  • 本文关键字:结构 rust rust macros
  • 更新时间 :
  • 英文 :


我想创建一个宏,在接收到的模型上生成具有所有字段的结构并实现trait Default,但遇到了这样的问题。我的宏struct_field!被识别为一个字段,而不是模型中的宏!Мaybe有人知道如何解决这个问题

macro_rules! struct_field {
($fild_name:ident: string = $def_val:expr,) => {
pub $fild_name: Arc<RwLock<String>>
};

($fild_name:ident: string = $def_val:expr, $($fields:tt)+) => {
pub $fild_name: Arc<RwLock<String>>
struct_field!($($fields)+)
};
($fild_name:ident: bool = $def_val:expr,) => {
pub enable_kernel_settings: Arc<AtomicBool>,
};
($fild_name:ident: bool = $def_val:expr, $($fields:tt)+) => {
pub $fild_name: Arc<AtomicBool>,
struct_field!($($fields)+)
};
}
macro_rules! model {
($model:ident { $($inner_model:ident : $inner_model_name:ident { $($fields:tt)+ },)+ }) => {
pub struct $model {$(
$inner_model: $inner_model_name,
)+}
$(pub struct $inner_model_name {
struct_field!($($fields)+) // <-- error
})+
};
}

错误:

error: expected `:`, found `!`
--> .../mod.rs:43:29
|
43 |                   struct_field!($($fields)+)
|                               ^ expected `:`
...
48 | / model! {
49 | |     MainStruct {
50 | |         inner_struct1: InnerStruct1 {
51 | |             feild1: bool = true,
...  |
58 | |     }
59 | | }
| |_- in this macro invocation

的例子:

model! {
MainStruct {
inner_struct1: InnerStruct1 {
feild1: bool = true,
},
inner_struct2: InnerStruct2 {
feild1: bool = false,
feild2: bool = false,
feild3: string = "ignore",
},
}
}

预期结果:

pub struct MainStruct {
inner_struct1: InnerStruct1,
inner_struct2: InnerStruct2,
}
pub struct InnerStruct1 {
feild1: Arc<AtomicBool>,
}
pub struct InnerStruct2 {
feild1: Arc<AtomicBool>,
feild2: Arc<AtomicBool>,
feild3: Arc<RwLock<String>>
}

您可以使用"cargo expand"进行测试。你应该启用rust-nightly

与类c宏相反,Rust宏只能在有效的AST节点上操作,也就是说,它们只能传递一些可以标记的东西,如果需要的话,还可以在一定程度上进行解析,并且只能"返回";有效的AST节点。特别是,这排除了将扩展为字段定义的宏的调用,因为像a: bool这样的东西不是有效的AST节点。

使用函数式的过程式宏,仍然可以让宏做你想做的事情,但它可能会变得更复杂。

最新更新