1 {-# LANGUAGE DefaultSignatures #-}
2 {-# LANGUAGE FlexibleContexts #-}
3 {-# LANGUAGE FlexibleInstances #-}
4 {-# LANGUAGE MultiParamTypeClasses #-}
5 {-# LANGUAGE ScopedTypeVariables #-}
6 {-# LANGUAGE TypeFamilies #-}
7 -- | Expression for 'Maybe'.
8 module Language.LOL.Symantic.Expr.Maybe where
10 import Data.Proxy (Proxy(..))
11 import Data.Type.Equality ((:~:)(Refl))
12 import Prelude hiding (maybe)
13 import Language.LOL.Symantic.Type
14 import Language.LOL.Symantic.Repr.Dup
15 import Language.LOL.Symantic.Trans.Common
16 import Language.LOL.Symantic.Expr.Common
17 import Language.LOL.Symantic.Expr.Lambda
18 import Language.LOL.Symantic.Expr.Bool
20 -- * Class 'Sym_Maybe'
22 class Sym_Maybe lam repr where
25 -> repr (Lambda lam a b)
32 -> t repr (Lambda lam a b)
35 maybe = trans_map3 maybe
36 class Sym_Maybe_Cons repr where
37 nothing :: repr (Maybe a)
38 just :: repr a -> repr (Maybe a)
40 default nothing :: Trans t repr => t repr (Maybe a)
41 default just :: Trans t repr => t repr a -> t repr (Maybe a)
42 nothing = trans_lift nothing
43 just = trans_map1 just
45 instance -- Sym_Maybe Dup
48 ) => Sym_Maybe lam (Dup r1 r2) where
49 maybe (m1 `Dup` m2) (n1 `Dup` n2) (j1 `Dup` j2) =
50 maybe m1 n1 j1 `Dup` maybe m2 n2 j2
51 instance -- Sym_Maybe_Cons Dup
54 ) => Sym_Maybe_Cons (Dup r1 r2) where
55 nothing = nothing `Dup` nothing
56 just (a1 `Dup` a2) = just a1 `Dup` just a2
58 -- * Type 'Expr_Maybe'
60 data Expr_Maybe (lam:: * -> *) (root:: *)
61 type instance Root_of_Expr (Expr_Maybe lam root) = root
62 type instance Type_of_Expr (Expr_Maybe lam root) = Type_Maybe
63 type instance Sym_of_Expr (Expr_Maybe lam root) repr = (Sym_Maybe lam repr, Sym_Maybe_Cons repr)
64 type instance Error_of_Expr ast (Expr_Maybe lam root) = No_Error_Expr
67 :: forall root lam ty ast hs ret.
68 ( ty ~ Type_Root_of_Expr (Expr_Maybe lam root)
69 , Type_Eq (Type_Root_of_Expr root)
71 , Type_Root_Lift (Type_Fun lam) (Type_Root_of_Expr root)
72 , Type_Root_Lift Type_Maybe (Type_Root_of_Expr root)
73 , Error_Expr_Lift (Error_Expr (Error_of_Type ast ty) ty ast)
74 (Error_of_Expr ast root)
75 , Type_Unlift (Type_Fun lam) (Type_of_Expr root)
76 , Type_Unlift Type_Maybe (Type_of_Expr root)
77 , Root_of_Expr root ~ root
78 ) => ast -> ast -> ast
79 -> Expr_From ast (Expr_Maybe lam root) hs ret
80 maybe_from ast_n ast_j ast_m ex ast ctx k =
81 expr_from (Proxy::Proxy root) ast_n ctx $
82 \(ty_n::Type_Root_of_Expr root h_n) (Forall_Repr_with_Context n) ->
83 expr_from (Proxy::Proxy root) ast_j ctx $
84 \(ty_j::Type_Root_of_Expr root h_j) (Forall_Repr_with_Context j) ->
85 expr_from (Proxy::Proxy root) ast_m ctx $
86 \(ty_m::Type_Root_of_Expr root h_m) (Forall_Repr_with_Context m) ->
87 case type_unlift $ unType_Root ty_j of
90 Error_Expr_Type_mismatch ast
91 (Exists_Type (type_var SZero `type_fun` type_var (SSucc SZero)
92 :: Type_Root_of_Expr (Expr_Maybe lam root) (lam Zero -> lam (Succ Zero))))
94 Just (ty_j_a `Type_Fun` ty_j_b
95 :: Type_Fun lam (Type_Root_of_Expr root) h_j) ->
96 case type_unlift $ unType_Root ty_m of
99 Error_Expr_Type_mismatch ast
100 (Exists_Type (type_maybe $ type_var SZero
101 :: Type_Root_of_Expr (Expr_Maybe lam root) (Maybe Zero)))
103 Just (Type_Maybe ty_m_a
104 :: Type_Maybe (Type_Root_of_Expr root) h_m) ->
106 ty_n ty_j_b $ \Refl ->
108 ty_m_a ty_j_a $ \Refl ->
109 k ty_n $ Forall_Repr_with_Context $
110 \c -> maybe (n c) (j c) (m c)
113 :: forall root lam ty ast hs ret.
114 ( ty ~ Type_Root_of_Expr (Expr_Maybe lam root)
115 , Type_from ast (Type_Root_of_Expr root)
116 , Type_Root_Lift Type_Maybe (Type_Root_of_Expr root)
117 , Error_Expr_Lift (Error_Expr (Error_of_Type ast ty) ty ast)
118 (Error_of_Expr ast root)
119 , Root_of_Expr root ~ root
121 -> Expr_From ast (Expr_Maybe lam root) hs ret
122 nothing_from ast_ty_a ex ast _ctx k =
124 (Proxy::Proxy (Type_Root_of_Expr root))
125 ast_ty_a (Right . Exists_Type) of
126 Left err -> Left $ error_expr ex $ Error_Expr_Type err ast
127 Right (Exists_Type (ty_a::Type_Root_of_Expr root h_a)) ->
128 k (type_maybe ty_a) $ Forall_Repr_with_Context $
132 :: forall root lam ty ast hs ret.
133 ( ty ~ Type_Root_of_Expr (Expr_Maybe lam root)
135 , Type_Root_Lift Type_Maybe (Type_Root_of_Expr root)
136 , Root_of_Expr root ~ root
138 -> Expr_From ast (Expr_Maybe lam root) hs ret
139 just_from ast_a _ex _ast ctx k =
140 expr_from (Proxy::Proxy root) ast_a ctx $
141 \(ty_a::Type_Root_of_Expr root h_a) (Forall_Repr_with_Context a) ->
142 k (type_maybe ty_a) $ Forall_Repr_with_Context $
145 -- ** Type 'Expr_Lambda_Maybe_Bool'
146 -- | Convenient alias.
147 type Expr_Lambda_Maybe_Bool lam
148 = Expr_Root (Expr_Alt (Expr_Lambda lam)
149 (Expr_Alt (Expr_Maybe lam)
152 -- | Convenient alias around 'expr_from'.
153 expr_lambda_maybe_bool_from
154 :: forall lam ast root.
155 ( Expr_from ast (Expr_Lambda_Maybe_Bool lam)
156 , root ~ Expr_Lambda_Maybe_Bool lam
159 -> Either (Error_of_Expr ast root)
160 (Exists_Type_and_Repr (Type_Root_of_Expr root)
162 expr_lambda_maybe_bool_from _lam ast =
163 expr_from (Proxy::Proxy root) ast
164 Context_Empty $ \ty (Forall_Repr_with_Context repr) ->
165 Right $ Exists_Type_and_Repr ty $
166 Forall_Repr $ repr Context_Empty