Given this simple macro that expands multiple items, how could this take a macro as an argument?
macro_rules! print_structs {
($($t:ty)*) => ($(
println!("{:?}", TypeId::of::<$t>());
)*)
}
// expands one println per type!
print_structs! { i8 i16 usize String }
How could a pre-defined macro of types be passed in?
Example of non-working macro:
macro_rules! some_types {
() => {
i8 i16 usize String
}
}
print_structs! { some_types!() }
See play.rust-lang.org example, uncomment UNCOMMENT TO TEST
lines to see the problem.
Gives the error: macro expansion ignores token `i16` and any following
I also tried to put the list in a file to include, eg:
print_structs! {
include!("some_types.in")
}
... however this gives an error: expected type, found `include!("../struct_list.rs")`
To do that, you create what are called arguments. You come up with a name for a variable that you can use in the macro and put it in the middle of the parentheses at the top of the macro. This argument can then be used within the macro as a regular variable.
To assign a macro that you pass arguments to a button, shape, image, or any object, you first right-click that object and click Assign Macro and then type the name of the macro and the argument, following the pattern described in the above examples, and then click OK.
A recursive macro is one that calls itself over and over to perform a specific task.
Macro parameter values are character sequences of no formal type, and they are comma delimited. There is no way to pass in a comma as part of a parameter value. The number of parameters passed can be less than, greater than, or equal to the number of parameters that the macro value is designed to receive.
From looking into this, it seems that its not possible to expand a list inside a macro using a macro or include
.
Although code-generation is an option, its quite involved so will leave it out of this answer.
It is possible to get similar functionality by swapping macro use around, instead of passing the list into a macro, pass a macro name into a generic macro that expand it with a list.
Heres a working example:
macro_rules! print_structs {
($($t:ty)*) => ($(
println!("{:?}", ::std::any::TypeId::of::<$t>());
)*)
}
macro_rules! apply_macro_to_structs {
($macro_id:ident) => {
$macro_id! {
i8 i16 usize String
}
}
}
fn test_a() {
// expands one println per type!
print_structs! { i8 i16 usize String }
}
fn test_b() {
// expand using a macro
apply_macro_to_structs!(print_structs);
}
fn main() {
test_a();
test_b();
}
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With