Allow 'newtype' syntax for tags
Doing this: tag foo = mytype; is now equivalent to doing this: tag foo { foo(mytype); }
This commit is contained in:
parent
fb72be0a89
commit
57e6340253
|
@ -945,7 +945,7 @@ fn parse_bottom_expr(&parser p) -> @ast::expr {
|
|||
hi = es.span.hi;
|
||||
ex = ast::expr_call(f, es.node);
|
||||
} else if (is_ident(p.peek()) && !is_word(p, "true") &&
|
||||
!is_word(p, "false")) {
|
||||
!is_word(p, "false")) {
|
||||
check_bad_word(p);
|
||||
auto pth = parse_path_and_ty_param_substs(p);
|
||||
hi = pth.span.hi;
|
||||
|
@ -1979,6 +1979,21 @@ fn parse_item_tag(&parser p, vec[ast::attribute] attrs) -> @ast::item {
|
|||
auto id = parse_ident(p);
|
||||
auto ty_params = parse_ty_params(p);
|
||||
let vec[ast::variant] variants = [];
|
||||
// Newtype syntax
|
||||
if (p.peek() == token::EQ) {
|
||||
if (p.get_bad_expr_words().contains_key(id)) {
|
||||
p.fatal("found " + id + " in tag constructor position");
|
||||
}
|
||||
p.bump();
|
||||
auto ty = parse_ty(p);
|
||||
expect(p, token::SEMI);
|
||||
auto variant = spanned(ty.span.lo, ty.span.hi,
|
||||
rec(name=id,
|
||||
args=[rec(ty=ty, id=p.get_id())],
|
||||
id=p.get_id()));
|
||||
ret mk_item(p, lo, ty.span.hi, id,
|
||||
ast::item_tag([variant], ty_params), attrs);
|
||||
}
|
||||
expect(p, token::LBRACE);
|
||||
while (p.peek() != token::RBRACE) {
|
||||
auto tok = p.peek();
|
||||
|
|
|
@ -383,27 +383,43 @@ fn print_item(&ps s, &@ast::item item) {
|
|||
break_offset(s.s, 0u, 0);
|
||||
}
|
||||
case (ast::item_tag(?variants, ?params)) {
|
||||
head(s, "tag");
|
||||
auto newtype = vec::len(variants) == 1u &&
|
||||
str::eq(item.ident, variants.(0).node.name) &&
|
||||
vec::len(variants.(0).node.args) == 1u;
|
||||
if (newtype) {
|
||||
ibox(s, indent_unit);
|
||||
word_space(s, "tag");
|
||||
} else {
|
||||
head(s, "tag");
|
||||
}
|
||||
word(s.s, item.ident);
|
||||
print_type_params(s, params);
|
||||
space(s.s);
|
||||
bopen(s);
|
||||
for (ast::variant v in variants) {
|
||||
space(s.s);
|
||||
maybe_print_comment(s, v.span.lo);
|
||||
word(s.s, v.node.name);
|
||||
if (vec::len(v.node.args) > 0u) {
|
||||
popen(s);
|
||||
fn print_variant_arg(&ps s, &ast::variant_arg arg) {
|
||||
print_type(s, *arg.ty);
|
||||
}
|
||||
commasep(s, consistent, v.node.args, print_variant_arg);
|
||||
pclose(s);
|
||||
}
|
||||
if (newtype) {
|
||||
word_space(s, "=");
|
||||
print_type(s, *variants.(0).node.args.(0).ty);
|
||||
word(s.s, ";");
|
||||
maybe_print_trailing_comment(s, v.span, none[uint]);
|
||||
end(s);
|
||||
} else {
|
||||
bopen(s);
|
||||
for (ast::variant v in variants) {
|
||||
space(s.s);
|
||||
maybe_print_comment(s, v.span.lo);
|
||||
word(s.s, v.node.name);
|
||||
if (vec::len(v.node.args) > 0u) {
|
||||
popen(s);
|
||||
fn print_variant_arg(&ps s, &ast::variant_arg arg) {
|
||||
print_type(s, *arg.ty);
|
||||
}
|
||||
commasep(s, consistent, v.node.args,
|
||||
print_variant_arg);
|
||||
pclose(s);
|
||||
}
|
||||
word(s.s, ";");
|
||||
maybe_print_trailing_comment(s, v.span, none[uint]);
|
||||
}
|
||||
bclose(s, item.span);
|
||||
}
|
||||
bclose(s, item.span);
|
||||
}
|
||||
case (ast::item_obj(?_obj, ?params, _)) {
|
||||
head(s, "obj");
|
||||
|
|
Loading…
Reference in New Issue