英文:
Rust macro to generate a macro
问题
I'm writing some macros that are all really similar (MWE the actual ones are much larger):
macro_rules! var1 {
() => {some_func(some_enum::Var1, vec![])};
($($e:expr),*) => {some_func(some_enum::Var1, vec![$($s),*])};
}
macro_rules! var2 {
() => {some_func(some_enum::Var2, vec![])};
($($e:expr),*) => {some_func(some_enum::Var2, vec![$($s),*])};
}
I instead decided to try different brackets
macro_rules! var {
() => {some_func(some_enum::Var1, vec![])};
($($e:expr),*) => {some_func(some_enum::Var1, vec![$($s),*])};
[] => {some_func(some_enum::Var2, vec![])};
[$($e:expr),*] => {some_func(some_enum::Var2, vec![$($s),*])};
}
which didn't work. This would have been my preferred method to do this so if you know how to do this that's be greatly appreciated.
I instead tried to use a macro to generate the other macros:
macro_rules! generator {
($t:ident, $s:expr) => {
macro_rules! $t {
() => {some_func($s:expr, vec![])};
($($e:expr),*) => {some_func($s:expr, vec![$($s),*])};
}
};
}
generator!(var1, some_enum::Var1);
generator!(var2, some_enum::Var2);
This gives me the error "attempted to repeat an expression containing no syntax variables matched as repeating at this depth" and I don't know what it means.
英文:
I'm writing some macros that are all really similar (MWE the actual ones are much larger):
macro_rules! var1 {
() => {some_func(some_enum::Var1, vec![])};
($($e:expr),*) => {some_func(some_enum::Var1, vec![$($s),*])};
}
macro_rules! var2 {
() => {some_func(some_enum::Var2, vec![])};
($($e:expr),*) => {some_func(some_enum::Var2, vec![$($s),*])};
}
I instead decided to try different brackets
macro_rules! var {
() => {some_func(some_enum::Var1, vec![])};
($($e:expr),*) => {some_func(some_enum::Var1, vec![$($s),*])};
[] => {some_func(some_enum::Var2, vec![])};
[$($e:expr),*] => {some_func(some_enum::Var2, vec![$($s),*])};
}
which didn't work. This would have been my preferred method to do this so if you know how to do this that's be greatly appreciated.
I instead tried to use a macro to generate the other macros:
macro_rules! generator {
($t:ident, $s:expr) => {
macro_rules! $t {
() => {some_func($s:expr, vec![])};
($($e:expr),*) => {some_func($s:expr, vec![$($s),*])};
}
};
}
generator!(var1, some_enum::Var1);
generator!(var2, some_enum::Var2);
This gives me the error "attempted to repeat an expression containing no syntax variables matched as repeating at this depth" andx I don't know what it means.
答案1
得分: 0
The error you're getting means that you use the repeat syntax $(),*
without a syntax variable in it, which you see when you look at the full error message:
错误消息的意思是,您在重复语法中使用了$(),*
,但没有包含语法变量,这是从完整的错误消息中可以看到的:
error: attempted to repeat an expression containing no syntax variables matched as repeating at this depth
--> src/main.rs:10:9
|
10 | ($($e:expr),*) => {some_func($s:expr, vec![$($e),*])};
| ^^^^^^^^^
The problem is you try to use the special syntax to define syntax variables inside of a macro where it has some different special meaning.
问题是,您尝试在宏中使用特殊语法来定义语法变量,而这在宏中具有不同的特殊含义。
You can get around it by simply escaping the $
that you do not wish to expand on the first macro invocation:
您可以通过在第一个宏调用中简单地转义您不希望展开的$
来解决这个问题:
macro_rules! generator {
($t:ident, $s:expr) => {
macro_rules! $t {
() => {some_func($s, vec![])};
($$($$e:expr),*) => {some_func($s, vec![$$($$e),*])};
}
}
}
But macro_metavar_expr
isn't stable yet so you have to add #![feature(macro_metavar_expr)]
at the top of your crate and compile with a nightly compiler.
但macro_metavar_expr
目前还不稳定,因此您需要在您的crate顶部添加#![feature(macro_metavar_expr)]
,并使用夜间编译器进行编译。
Note: added ;
after the macro branches and fixed some other syntax errors in there as well.
注意:在宏分支后面添加了;
,还修复了其中的一些其他语法错误。
英文:
The error you're getting means that you use the repeat syntax $(),*
without a syntax variable in it, which you see when you look at the full error message:
error: attempted to repeat an expression containing no syntax variables matched as repeating at this depth
--> src/main.rs:10:9
|
10 | ($($e:expr),*) => {some_func($s:expr, vec![$($e),*])};
| ^^^^^^^^^
The problem is you try to use the special syntax to define syntax variables inside of a macro where it has some different special meaning.
You can get around it by simply escaping the $
that you do not wish to expand on the first macro invocation:
macro_rules! generator {
($t:ident, $s:expr) => {
macro_rules! $t {
() => {some_func($s, vec![])};
($$($$e:expr),*) => {some_func($s, vec![$$($$e),*])};
}
}
}
But macro_metavar_expr
isn't stable yet so you have to add #![feature(macro_metavar_expr)]
at the top of your crate and compile with a nightly compiler.
Note: added ;
after the macro branches and fixed some other syntax errors in there as well.
通过集体智慧和协作来改善编程学习和解决问题的方式。致力于成为全球开发者共同参与的知识库,让每个人都能够通过互相帮助和分享经验来进步。
评论