Fixed pretty printing and pattern split (#111)

This commit is contained in:
Radosław Rowicki 2019-07-29 13:27:01 +02:00 committed by Dincho Todorov
parent 4bf382a997
commit 045df292be
3 changed files with 59 additions and 9 deletions

View File

@ -681,7 +681,7 @@ split_pat({con, As, I, Pats}) ->
Xs = [fresh_name() || _ <- Pats], Xs = [fresh_name() || _ <- Pats],
{{con, As, I, Xs}, Pats}; {{con, As, I, Xs}, Pats};
split_pat({tuple, Pats}) -> split_pat({tuple, Pats}) ->
Xs = [{var, fresh_name()} || _ <- Pats], Xs = [fresh_name() || _ <- Pats],
{{tuple, Xs}, Pats}. {{tuple, Xs}, Pats}.
-spec split_vars(fsplit_pat(), ftype()) -> [{var_name(), ftype()}]. -spec split_vars(fsplit_pat(), ftype()) -> [{var_name(), ftype()}].
@ -1094,6 +1094,16 @@ pat_vars({tuple, Ps}) -> pat_vars(Ps);
pat_vars({con, _, _, Ps}) -> pat_vars(Ps); pat_vars({con, _, _, Ps}) -> pat_vars(Ps);
pat_vars(Ps) when is_list(Ps) -> [X || P <- Ps, X <- pat_vars(P)]. pat_vars(Ps) when is_list(Ps) -> [X || P <- Ps, X <- pat_vars(P)].
-spec fsplit_pat_vars(fsplit_pat()) -> [var_name()].
fsplit_pat_vars({var, X}) -> [X || X /= "_"];
fsplit_pat_vars({bool, _}) -> [];
fsplit_pat_vars({int, _}) -> [];
fsplit_pat_vars({string, _}) -> [];
fsplit_pat_vars(nil) -> [];
fsplit_pat_vars({'::', P, Q}) -> [P, Q];
fsplit_pat_vars({tuple, Ps}) -> Ps;
fsplit_pat_vars({con, _, _, Ps}) -> Ps.
free_vars(Xs) when is_list(Xs) -> free_vars(Xs) when is_list(Xs) ->
lists:umerge([ free_vars(X) || X <- Xs ]); lists:umerge([ free_vars(X) || X <- Xs ]);
free_vars(Expr) -> free_vars(Expr) ->
@ -1119,7 +1129,7 @@ free_vars(Expr) ->
{switch, A} -> free_vars(A); {switch, A} -> free_vars(A);
{split, _, X, As} -> free_vars([{var, X} | As]); {split, _, X, As} -> free_vars([{var, X} | As]);
{nosplit, A} -> free_vars(A); {nosplit, A} -> free_vars(A);
{'case', P, A} -> free_vars(A) -- lists:sort(pat_vars(P)) {'case', P, A} -> free_vars(A) -- lists:sort(fsplit_pat_vars(P))
end. end.
get_named_args(NamedArgsT, Args) -> get_named_args(NamedArgsT, Args) ->
@ -1285,7 +1295,10 @@ pp_fun_name({local_fun, Q}) -> pp_text(string:join(Q, ".")).
pp_text(<<>>) -> prettypr:text("\"\""); pp_text(<<>>) -> prettypr:text("\"\"");
pp_text(Bin) when is_binary(Bin) -> prettypr:text(lists:flatten(io_lib:format("~p", [binary_to_list(Bin)]))); pp_text(Bin) when is_binary(Bin) -> prettypr:text(lists:flatten(io_lib:format("~p", [binary_to_list(Bin)])));
pp_text(S) -> prettypr:text(lists:concat([S])). pp_text(S) when is_list(S) -> prettypr:text(lists:concat([S]));
pp_text(A) when is_atom(A) -> prettypr:text(atom_to_list(A)).
pp_int(I) -> prettypr:text(integer_to_list(I)).
pp_beside([]) -> prettypr:empty(); pp_beside([]) -> prettypr:empty();
pp_beside([X]) -> X; pp_beside([X]) -> X;
@ -1317,18 +1330,18 @@ pp_fexpr(nil) ->
pp_fexpr({var, X}) -> pp_text(X); pp_fexpr({var, X}) -> pp_text(X);
pp_fexpr({def, Fun}) -> pp_fun_name(Fun); pp_fexpr({def, Fun}) -> pp_fun_name(Fun);
pp_fexpr({def_u, Fun, Ar}) -> pp_fexpr({def_u, Fun, Ar}) ->
pp_beside([pp_fun_name(Fun), pp_text("/"), pp_text(Ar)]); pp_beside([pp_fun_name(Fun), pp_text("/"), pp_int(Ar)]);
pp_fexpr({def, Fun, Args}) -> pp_fexpr({def, Fun, Args}) ->
pp_call(pp_fun_name(Fun), Args); pp_call(pp_fun_name(Fun), Args);
pp_fexpr({con, _, I, []}) -> pp_fexpr({con, _, I, []}) ->
pp_beside(pp_text("C"), pp_text(I)); pp_beside(pp_text("C"), pp_int(I));
pp_fexpr({con, _, I, Es}) -> pp_fexpr({con, _, I, Es}) ->
pp_beside(pp_fexpr({con, [], I, []}), pp_beside(pp_fexpr({con, [], I, []}),
pp_fexpr({tuple, Es})); pp_fexpr({tuple, Es}));
pp_fexpr({tuple, Es}) -> pp_fexpr({tuple, Es}) ->
pp_parens(pp_par(pp_punctuate(pp_text(","), [pp_fexpr(E) || E <- Es]))); pp_parens(pp_par(pp_punctuate(pp_text(","), [pp_fexpr(E) || E <- Es])));
pp_fexpr({proj, E, I}) -> pp_fexpr({proj, E, I}) ->
pp_beside([pp_fexpr(E), pp_text("."), pp_text(I)]); pp_beside([pp_fexpr(E), pp_text("."), pp_int(I)]);
pp_fexpr({lam, Xs, A}) -> pp_fexpr({lam, Xs, A}) ->
pp_par([pp_fexpr({tuple, [{var, X} || X <- Xs]}), pp_text("=>"), pp_par([pp_fexpr({tuple, [{var, X} || X <- Xs]}), pp_text("=>"),
prettypr:nest(2, pp_fexpr(A))]); prettypr:nest(2, pp_fexpr(A))]);
@ -1339,7 +1352,7 @@ pp_fexpr({closure, Fun, ClEnv}) ->
end, end,
pp_call(pp_text("__CLOSURE__"), [{def, Fun} | FVs]); pp_call(pp_text("__CLOSURE__"), [{def, Fun} | FVs]);
pp_fexpr({set_proj, E, I, A}) -> pp_fexpr({set_proj, E, I, A}) ->
pp_beside(pp_fexpr(E), pp_braces(pp_beside([pp_text(I), pp_text(" = "), pp_fexpr(A)]))); pp_beside(pp_fexpr(E), pp_braces(pp_beside([pp_int(I), pp_text(" = "), pp_fexpr(A)])));
pp_fexpr({op, Op, [A, B] = Args}) -> pp_fexpr({op, Op, [A, B] = Args}) ->
case is_infix(Op) of case is_infix(Op) of
false -> pp_call(pp_text(Op), Args); false -> pp_call(pp_text(Op), Args);
@ -1360,7 +1373,7 @@ pp_fexpr({builtin_u, B, N}) ->
pp_fexpr({builtin, B, As}) -> pp_fexpr({builtin, B, As}) ->
pp_call(pp_text(B), As); pp_call(pp_text(B), As);
pp_fexpr({remote_u, Ct, Fun, Ar}) -> pp_fexpr({remote_u, Ct, Fun, Ar}) ->
pp_beside([pp_fexpr(Ct), pp_text("."), pp_fun_name(Fun), pp_text("/"), pp_text(Ar)]); pp_beside([pp_fexpr(Ct), pp_text("."), pp_fun_name(Fun), pp_text("/"), pp_int(Ar)]);
pp_fexpr({remote, Ct, Fun, As}) -> pp_fexpr({remote, Ct, Fun, As}) ->
pp_call(pp_beside([pp_fexpr(Ct), pp_text("."), pp_fun_name(Fun)]), As); pp_call(pp_beside([pp_fexpr(Ct), pp_text("."), pp_fun_name(Fun)]), As);
pp_fexpr({funcall, Fun, As}) -> pp_fexpr({funcall, Fun, As}) ->

View File

@ -117,7 +117,8 @@ compilable_contracts() ->
"address_chain", "address_chain",
"namespace_bug", "namespace_bug",
"bytes_to_x", "bytes_to_x",
"aens" "aens",
"tuple_match"
]. ].
not_yet_compilable(fate) -> []; not_yet_compilable(fate) -> [];

View File

@ -0,0 +1,36 @@
contract TuplesMatch =
entrypoint tuplify3() = (t) => switch(t)
(x, y, z) => 3
entrypoint fst(p : (int, string)) =
switch(p)
(x, y) => x
entrypoint fst'(p : (int, string)) =
switch(p)
(x, _) => x
entrypoint snd(p : (int, string)) =
switch(p)
(x, y) => y
entrypoint snd'(p : (int, string)) =
switch(p)
(_, y) => y
entrypoint sum(p) =
switch(p)
(x, y) => x + y
entrypoint swap(p : (int, string)) =
switch(p)
(x, y) => (y, x)
entrypoint id(p : (int, int, string)) =
switch(p)
(x, y, z) => (x, y, z)
entrypoint nest(p : ((int, int), string)) =
switch(p)
(xy, z) => switch(xy) (x, y) => (x, y, z)
entrypoint deep(p : ((int, int), (int, int))) =
switch(p)
((x, y), (z, w)) => (x, y, z, w)
entrypoint deep_sum(p : ((int, int), (int, int))) =
switch(p)
((x, y), (z, w)) => x + y + z + w