Skip to content

Commit 05f5d28

Browse files
syntax for defining implicit funcs
1 parent 19d6c08 commit 05f5d28

File tree

3 files changed

+42
-16
lines changed

3 files changed

+42
-16
lines changed

src/mo_frontend/parser.mly

Lines changed: 12 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -98,11 +98,14 @@ let rec normalize_let p e =
9898
| ParP p' -> normalize_let p' e
9999
| _ -> (p, e)
100100

101-
let let_or_exp named x e' at =
101+
let let_or_exp named x implicit e' at =
102102
if named
103-
then LetD(VarP x @! x.at, e' @? at, None) @? at
103+
then match implicit with
104+
| None -> LetD(VarP x @! x.at, e' @? at, None) @? at
104105
(* If you change the above regions,
105106
modify is_sugared_func_or_module to match *)
107+
| Some(implicit) ->
108+
LetD(ImplicitP { id = x; implicit } @! x.at, e' @? at, None) @? at
106109
else ExpD(e' @? at) @? at
107110

108111
let is_sugared_func_or_module dec = match dec.it with
@@ -894,7 +897,6 @@ pat_plain :
894897
{ VarP(x) @! at $sloc }
895898
| implicit x=id
896899
{ ImplicitP { implicit = x; id = x; } @! at $sloc }
897-
(* TODO *)
898900
| implicit LPAR x=id RPAR y=id
899901
{ ImplicitP { implicit = x; id = y; } @! at $sloc }
900902
| l=lit
@@ -952,10 +954,11 @@ pat_opt :
952954
{ fun sloc -> WildP @! sloc }
953955

954956
func_pat :
955-
| xf=id_opt ts=typ_params_opt p=pat_plain { (xf, ts, p) }
957+
| xf=id_opt ts=typ_params_opt p=pat_plain { (xf, None, ts, p) }
958+
| implicit x=id ts=typ_params_opt p=pat_plain { ((fun _ _ -> true, x), Some(x), ts, p) }
959+
| implicit LPAR x=id RPAR y=id ts=typ_params_opt p=pat_plain { ((fun _ _ -> true, y), Some(x), ts, p) }
956960

957961
(* Declarations *)
958-
959962
dec_var :
960963
| VAR x=id t=annot_opt EQ e=exp(ob)
961964
{ VarD(x, annot_exp e t) @? at $sloc }
@@ -971,10 +974,10 @@ dec_nonvar :
971974
{ (* This is a hack to support local func declarations that return a computed async.
972975
These should be defined using RHS syntax EQ e to avoid the implicit AsyncE introduction
973976
around bodies declared as blocks *)
974-
let xf, tps, p = xf_tps_p in
977+
let xf, i, tps, p = xf_tps_p in
975978
let named, x = xf "func" $sloc in
976979
let is_sugar, e = desugar_func_body sp x t fb in
977-
let_or_exp named x (func_exp x.it sp tps p t is_sugar e) (at $sloc) }
980+
let_or_exp named x i (func_exp x.it sp tps p t is_sugar e) (at $sloc) }
978981
| eo=parenthetical_opt mk_d=obj_or_class_dec { mk_d eo }
979982
| MIXIN p=pat_plain dfs=obj_body {
980983
let dfs = List.map (share_dec_field (Stable @@ no_region)) dfs in
@@ -1001,12 +1004,12 @@ obj_or_class_dec :
10011004
@? at $sloc) @? at $sloc
10021005
else objblock eo { s with note = persistent } None t efs @? at $sloc
10031006
in
1004-
let_or_exp named x e.it e.at }
1007+
let_or_exp named x None e.it e.at }
10051008
| sp=shared_pat_opt ds=obj_sort_opt CLASS
10061009
xf_tps_p=func_pat t=annot_opt cb=class_body
10071010
{ fun eo ->
10081011
let (persistent, s) = ds in
1009-
let xf, tps, p = xf_tps_p in
1012+
let xf, _, tps, p = xf_tps_p in
10101013
let (_, id) = xf "class" $sloc in
10111014
let cid = id.it @= id.at in
10121015
let x, dfs = cb in
Lines changed: 25 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,25 @@
1+
import Text "../core-stub/src/Text";
2+
import Nat "../core-stub/src/Nat";
3+
import Map "../core-stub/src/Map";
4+
import { type Order } "../core-stub/src/Types";
5+
6+
actor {
7+
type User = { name : Text };
8+
type Invoice = { id : Nat };
9+
10+
func implicit(compare) compareUser(self : User, other : User) : Order {
11+
Text.compare(self.name, other.name)
12+
};
13+
14+
func implicit(compare) compareInvoice(self : Invoice, other : Invoice) : Order {
15+
Nat.compare(self.id, other.id)
16+
};
17+
18+
let users = Map.empty<User, ()>();
19+
let invoices = Map.empty<Invoice, ()>();
20+
21+
users.add({ name = "foo" }, ());
22+
invoices.add({ id = 10 }, ());
23+
}
24+
25+
//SKIP comp

test/run/implicit-pat.mo

Lines changed: 5 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -16,13 +16,10 @@ two();
1616
assert addOne() == 1;
1717

1818
module DumbHash {
19-
func hashNat_(_ : Nat) : Nat { 1 };
20-
func hashInt_(_ : Int) : Nat { 2 };
21-
func hashText_(_ : Text) : Nat { 3 };
22-
23-
public let implicit(hashFn) hashNat : Nat -> Nat = hashNat_;
24-
public let implicit(hashFn) hashInt : Int -> Nat = hashInt_;
25-
public let implicit(hashFn) hashText : Text -> Nat = hashText_;
19+
public func implicit(hashFn) hashNat(_ : Nat) : Nat { 1 };
20+
public func implicit(hashFn) hashInt(_ : Int) : Nat { 2 };
21+
public func implicit(hashFn) hashText(_ : Text) : Nat { 3 };
22+
public func implicit hashFn(_ : Char) : Nat { 4 };
2623
};
2724

2825
func hash<T>(self : T, hashFn : (implicit : T -> Nat)) : Nat {
@@ -32,3 +29,4 @@ func hash<T>(self : T, hashFn : (implicit : T -> Nat)) : Nat {
3229
assert hash(42) == 1;
3330
assert hash(-2) == 2;
3431
assert hash("Hello") == 3;
32+
assert hash('H') == 4;

0 commit comments

Comments
 (0)