我正在尝试编写一些我自己的调试宏,并在dbg!中查看用于锈迹生成的源代码
macro_rules! dbg {
() => {
$crate::eprintln!("[{}:{}]", $crate::file!(), $crate::line!());
};
($val:expr $(,)?) => {
// Use of `match` here is intentional because it affects the lifetimes
// of temporaries - https://stackoverflow.com/a/48732525/1063961
match $val {
tmp => {
$crate::eprintln!("[{}:{}] {} = {:#?}",
$crate::file!(), $crate::line!(), $crate::stringify!($val), &tmp);
tmp
}
}
};
($($val:expr),+ $(,)?) => {
($($crate::dbg!($val)),+,)
};
}有几件事让我对这段代码感到困惑:
$操作符在做什么?($val:expr $(,)?)?我不明白,是什么以及它为什么在那里。() => {$crate::eprintln!("[{}:{}]", $crate::file!(), $crate::line!());};开头发布于 2021-01-28 23:10:00
在这段代码中,$ operator在做什么?
macro_rules!在普通锈蚀之上有不同的语法。$s用于表示元数据(如$ident)和重复(如$(...))。您可能应该对Rust宏是什么做一些初步研究:
什么是平面语言等价于
($val:expr $(,)?)?我不明白,是什么以及它为什么在那里。
$val:expr定义了与单个表达式匹配的模式。$(,)?匹配可能存在0次或1次的,。有效地使它能够使dbg!允许可选的后缀逗号(以便模仿大部分锈蚀)。您将在另一个模式$($val:expr),+ $(,)?中看到这一点。
为什么宏定义以
() => {$crate::eprintln!("[{}:{}]", $crate::file!(), $crate::line!());};开头?
此宏设计为使用任意数量的参数调用,包括零。() => { ... };模式允许dbg!()有效。调用不带参数的dbg!的效果是只记录文件和行号。
https://stackoverflow.com/questions/65946195
复制相似问题