Да, и нет.
Прежде всего, concat!
генерирует строку, поэтому ваш код по сути такой же, как если бы вы написали:
fn main() {
"foobool(true)";
"fooi32(1)";
}
, что не op.
Чтобы сгенерировать Rust-код, макросу не нужно включать строки вообще:
macro_rules! foo {
($suffix:tt, $arg:expr) => {
$suffix($arg);
};
}
, который можно назвать foo!(foo_bool, true);
.
Если, однако, вы хотите создать имя foo_bool
из foo
и bool
, вам нужно использовать concat_idents
, который в настоящее время нестабилен и вряд ли скоро станет стабильным (поскольку это вызывает некоторую гигиену выпуски):
#![feature(concat_idents)]
macro_rules! foo {
($suffix:tt, $arg:expr) => {
concat_idents!(foo_, $suffix)($arg);
};
}
fn foo_i32(x: i32) {
println!("i32 {}", x);
}
fn foo_bool(x: bool) {
println!("bool {}", x);
}
fn main() {
foo!(bool, true);
foo!(i32, 1);
}