macro_rules! tp { ($n:ident) => { ... }; ($n:ident($($x:expr),*)) => { ... }; ($n:ident($($x:expr,)*)) => { ... }; ($n:expr) => { ... }; (@arrow[$x:expr]) => { ... }; (@arrow[$x:expr, $($xs:expr),*]) => { ... }; (@arrow[$x:expr, $($xs:expr,)*]) => { ... }; }
Expand description
Creates a Type
(convenience for common patterns).
Specifically, a Type<&'static str>
, where all names are static strings.
ⓘ
// Equivalent to:
Type::Constructed(ident, vec![
tp1,
tp2,
...
])
// or
Type::Variable(n)
// or
Type::arrow(
tp0,
Type::arrow(
tp1,
Type::arrow(
tp2,
...,
)
)
)
Examples
Make a primitive type:
let t = tp!(int);
assert_eq!(format!("{}", t), "int");
// Equivalent to:
let t_eq = Type::Constructed("int", vec![]);
assert_eq!(t, t_eq);
Make a variable type:
let t = tp!(0);
assert_eq!(format!("{}", t), "t0");
// Equivalent to:
let t_eq = Type::Variable(0);
assert_eq!(t, t_eq);
Make a composite type:
let tint = tp!(int);
let tstr = tp!(str);
let t = tp!(dict(tstr, tint));
assert_eq!(format!("{}", t), "dict(str,int)");
// Equivalent to:
let t_eq = Type::Constructed("dict", vec![
Type::Constructed("str", vec![]),
Type::Constructed("int", vec![]),
]);
assert_eq!(t, t_eq);
Make an arrow:
let t = tp!(@arrow[Type::Variable(0), Type::Variable(1), Type::Variable(2)]);
assert_eq!(format!("{}", t), "t0 → t1 → t2");
// Equivalent to:
let t_eq = Type::arrow(
Type::Variable(0),
Type::arrow(
Type::Variable(1),
Type::Variable(2),
)
);
assert_eq!(t, t_eq);
Nest them for more complex types:
// mapi: (int → α → β) → [α] → [β]
let t = tp!(@arrow[
tp!(@arrow[tp!(int), tp!(0), tp!(1)]),
tp!(list(tp!(0))),
tp!(list(tp!(1))),
]);
assert_eq!(format!("{}", t), "(int → t0 → t1) → list(t0) → list(t1)");