是否可以在 Rust 的过程宏中存储状态?
Is it possible to store state within Rust's procedural macros?
是否可以构建一个不输出任何内容,而是存储状态以构建列表的宏,然后再创建一个实际使用该数据的宏?
例如:
trait SomeTrait {}
#[derive(mark)]
struct Person {}
impl SomeTrait for Person {}
#[derive(mark)]
struct Item {}
impl SomeTrait for Item {}
#[derive(mark)]
struct Object {}
impl SomeTrait for Object {}
create_mapper! // this then outputs the below function
//assuming for the fact that data is loaded correctly before this macro is used
fn select_item(kind: String) -> impl SomeTrait {
match kind {
"person" => Person,
"item" => Item,
"object" => Object,
}
}
目前没有正式支持的方式来存储可由两个不同的 proc 宏调用使用的状态。我在讨论这个问题的地方创建了 this very related issue。
存储状态当然是可能的,但只是以一种 hacky 的方式。例如,您可以将所有状态序列化为 /tmp/my-state
。或者您可以尝试使用 static
全局变量。但即使这现在有效,也不能保证将来有效。另一个问题:由于增量编译,不能保证你所有的 proc 宏调用都被实际执行。因此,如果您有一个生成状态的宏和一个读取它的宏,如果第一个未执行,就会发生非常奇怪的事情。所以存储全局状态在技术上是可行的,但不可取。
在上面链接的问题中,您可以看到 MsleepyPanda proposed a possible solution,但我们还远未实现它。
是否可以构建一个不输出任何内容,而是存储状态以构建列表的宏,然后再创建一个实际使用该数据的宏?
例如:
trait SomeTrait {}
#[derive(mark)]
struct Person {}
impl SomeTrait for Person {}
#[derive(mark)]
struct Item {}
impl SomeTrait for Item {}
#[derive(mark)]
struct Object {}
impl SomeTrait for Object {}
create_mapper! // this then outputs the below function
//assuming for the fact that data is loaded correctly before this macro is used
fn select_item(kind: String) -> impl SomeTrait {
match kind {
"person" => Person,
"item" => Item,
"object" => Object,
}
}
目前没有正式支持的方式来存储可由两个不同的 proc 宏调用使用的状态。我在讨论这个问题的地方创建了 this very related issue。
存储状态当然是可能的,但只是以一种 hacky 的方式。例如,您可以将所有状态序列化为 /tmp/my-state
。或者您可以尝试使用 static
全局变量。但即使这现在有效,也不能保证将来有效。另一个问题:由于增量编译,不能保证你所有的 proc 宏调用都被实际执行。因此,如果您有一个生成状态的宏和一个读取它的宏,如果第一个未执行,就会发生非常奇怪的事情。所以存储全局状态在技术上是可行的,但不可取。
在上面链接的问题中,您可以看到 MsleepyPanda proposed a possible solution,但我们还远未实现它。