1
這裏是一個宏觀的,我想實現一個RPC庫我工作的簡化版本:爲什麼此宏調用導致未解析的名稱?
#[macro_export]
macro_rules! msgpack_rpc {
(
$(
rpc $name:ident ($($arg:ident : $arg_ty:ty),*) -> $ret_ty:ty | $err_ty:ty;
)+
) => (
pub trait Service {
$(
fn $name (&self, $($arg : $arg_ty),*) -> Result<$ret_ty, $err_ty>;
)+
}
pub struct Server;
impl Server {
pub fn listen<S>(handle: &(), address:(), service: S)
-> ::std::io::Result<()>
where S: Service + Send + Sync + 'static {
let service = move |msg: &str| {
let result = match msg {
$(
stringify!($name) => {
service.$name($($arg),*)
.map(String::from)
.map_err(String::from)
}
),+,
_ => String::from("method not supported".into()),
};
};
Ok(())
}
}
)
}
msgpack_rpc! {
rpc echo(arg: i64) -> i64 |();
}
宏擴展失敗,此錯誤編譯:
error: unresolved name `arg` [--explain E0425]
--> <anon>:40:17
|>
40 |> rpc echo(arg: i64) -> i64 |();
|> ^
<anon>:39:1: 41:2: note: in this expansion of msgpack_rpc! (defined in <anon>)
從閱讀類似的問題,我知道macro_rules
有時會擴大陳述的問題。不過,我很困惑,爲什麼它在這種情況下擴大項目有困難。
是否有解決方法來解決擴展問題?
您是否試過將'Service'和'Server'名稱作爲宏參數提供? –
不,我希望宏只聲明內聯項,並希望用戶在需要命名空間的情況下在模塊內擴展。 – euclio
請注意,在這種情況下創建[MCVE]非常有用;這是所有優秀程序員都應具備的技能。這裏是[這種情況下一個潛在的MCVE](http://play.integer32.com/?gist=79165c85749c3707b1149a5bd12862ec)。一旦你製作了一個MCVE,問題通常會變得更加明顯。 – Shepmaster