diff options
author | Gregor Kleen <pngwjpgh@users.noreply.github.com> | 2016-07-31 00:23:23 +0200 |
---|---|---|
committer | Gregor Kleen <pngwjpgh@users.noreply.github.com> | 2016-07-31 00:23:23 +0200 |
commit | d22086666632b707aa210f20ecf10a8cd4e6d4fe (patch) | |
tree | dd561d380898dfb0a0e8fc6d98249c965c19c221 /events/src/Events/Spec | |
parent | 41d0a0c8c3a66ce48756ad8c2ab0ea87933047c9 (diff) | |
download | events-d22086666632b707aa210f20ecf10a8cd4e6d4fe.tar events-d22086666632b707aa210f20ecf10a8cd4e6d4fe.tar.gz events-d22086666632b707aa210f20ecf10a8cd4e6d4fe.tar.bz2 events-d22086666632b707aa210f20ecf10a8cd4e6d4fe.tar.xz events-d22086666632b707aa210f20ecf10a8cd4e6d4fe.zip |
Lambda calculus for computing events at runtime
Diffstat (limited to 'events/src/Events/Spec')
-rw-r--r-- | events/src/Events/Spec/Eval.hs | 38 | ||||
-rw-r--r-- | events/src/Events/Spec/LICENSE | 29 | ||||
-rw-r--r-- | events/src/Events/Spec/Types.hs | 32 |
3 files changed, 99 insertions, 0 deletions
diff --git a/events/src/Events/Spec/Eval.hs b/events/src/Events/Spec/Eval.hs new file mode 100644 index 0000000..3a23e0b --- /dev/null +++ b/events/src/Events/Spec/Eval.hs | |||
@@ -0,0 +1,38 @@ | |||
1 | {-# LANGUAGE GADTs, DataKinds, TypeOperators, RankNTypes, ScopedTypeVariables #-} | ||
2 | |||
3 | module Events.Spec.Eval | ||
4 | ( evalExpr | ||
5 | ) where | ||
6 | |||
7 | import Events.Spec.Types | ||
8 | |||
9 | shift :: forall m ts2 t x. Expr m ts2 x -> Expr m (t ': ts2) x | ||
10 | shift = shift' LZ | ||
11 | where | ||
12 | -- shift' :: forall ts1 ts2 t x. Length ts1 -> Expr (ts1 ++ ts2) x -> Expr (ts1 ++ t ': ts2) x | ||
13 | shift' :: forall ts1 x. Length ts1 -> Expr m (ts1 ++ ts2) x -> Expr m (ts1 ++ t ': ts2) x | ||
14 | shift' _ (ELit x) = ELit x | ||
15 | shift' l (EVar v) = EVar $ shiftElem l v | ||
16 | shift' l (ELam b) = ELam $ shift' (LS l) b | ||
17 | shift' l (EApp f x) = EApp (shift' l f) (shift' l x) | ||
18 | |||
19 | shiftElem :: forall ts1 u. Length ts1 -> Elem u (ts1 ++ ts2) -> Elem u (ts1 ++ t ': ts2) | ||
20 | shiftElem LZ e = ES e | ||
21 | shiftElem (LS _) EZ = EZ | ||
22 | shiftElem (LS l) (ES e) = ES $ shiftElem l e | ||
23 | |||
24 | |||
25 | beta = flip beta' LZ | ||
26 | beta' :: forall m ts1 ts2 s t. Expr m ts2 s -> Length ts1 -> Expr m (ts1 ++ s ': ts2) t -> Expr m (ts1 ++ ts2) t | ||
27 | beta' _ _ (ELit x) = ELit x | ||
28 | beta' e LZ (EVar EZ ) = e | ||
29 | beta' _ LZ (EVar (ES v)) = EVar v | ||
30 | beta' _ (LS _) (EVar EZ ) = EVar EZ | ||
31 | beta' e (LS l) (EVar (ES v)) = shift $ beta' e l (EVar v) | ||
32 | beta' e l (ELam b) = ELam $ beta' e (LS l) b | ||
33 | beta' e l (EApp f a) = EApp (beta' e l f) (beta' e l a) | ||
34 | |||
35 | evalExpr :: Expr m '[] t -> Val m t | ||
36 | evalExpr (ELit a) = a | ||
37 | evalExpr (ELam a) = a | ||
38 | evalExpr (EApp f a) = evalExpr $ beta a (evalExpr f) | ||
diff --git a/events/src/Events/Spec/LICENSE b/events/src/Events/Spec/LICENSE new file mode 100644 index 0000000..c28fee7 --- /dev/null +++ b/events/src/Events/Spec/LICENSE | |||
@@ -0,0 +1,29 @@ | |||
1 | The code in siblings of this file is either heavily inspired by or copied from [glambda](https://hackage.haskell.org/package/glamba), an interpreter for a simply typed lambda-calculus by Richard Eisenberg under the following license: | ||
2 | |||
3 | Copyright (c) 2015, Richard Eisenberg | ||
4 | All rights reserved. | ||
5 | |||
6 | Redistribution and use in source and binary forms, with or without | ||
7 | modification, are permitted provided that the following conditions are met: | ||
8 | |||
9 | 1. Redistributions of source code must retain the above copyright notice, this | ||
10 | list of conditions and the following disclaimer. | ||
11 | |||
12 | 2. Redistributions in binary form must reproduce the above copyright notice, | ||
13 | this list of conditions and the following disclaimer in the documentation | ||
14 | and/or other materials provided with the distribution. | ||
15 | |||
16 | 3. Neither the name of the author nor the names of its contributors may be | ||
17 | used to endorse or promote products derived from this software without | ||
18 | specific prior written permission. | ||
19 | |||
20 | THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" | ||
21 | AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE | ||
22 | IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE | ||
23 | DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE | ||
24 | FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL | ||
25 | DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR | ||
26 | SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER | ||
27 | CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, | ||
28 | OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE | ||
29 | OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. \ No newline at end of file | ||
diff --git a/events/src/Events/Spec/Types.hs b/events/src/Events/Spec/Types.hs new file mode 100644 index 0000000..665958d --- /dev/null +++ b/events/src/Events/Spec/Types.hs | |||
@@ -0,0 +1,32 @@ | |||
1 | {-# LANGUAGE GADTs, DataKinds, PolyKinds, TypeOperators, KindSignatures, TypeFamilies, ExplicitNamespaces #-} | ||
2 | |||
3 | module Events.Spec.Types | ||
4 | ( Expr(..) | ||
5 | , Val(..) | ||
6 | , Elem(..) | ||
7 | , Length(..) | ||
8 | , type (++)(..) | ||
9 | ) where | ||
10 | |||
11 | data Expr :: (* -> *) -> [*] -> * -> * where | ||
12 | ELit :: Val m a -> Expr m ctx a | ||
13 | EVar :: Elem a ctx -> Expr m ctx a | ||
14 | ELam :: Expr m (arg ': ctx) res -> Expr m ctx (arg -> res) | ||
15 | EApp :: Expr m ctx (arg -> a) -> Expr m ctx arg -> Expr m ctx a | ||
16 | |||
17 | type family Val m a where | ||
18 | Val m (a -> b) = Expr m '[a] b | ||
19 | Val m a = m a | ||
20 | |||
21 | data Elem :: a -> [a] -> * where | ||
22 | EZ :: Elem x (x ': xs) | ||
23 | ES :: Elem x xs -> Elem x (y ': xs) | ||
24 | |||
25 | data Length :: [a] -> * where | ||
26 | LZ :: Length '[] | ||
27 | LS :: Length xs -> Length (x ': xs) | ||
28 | |||
29 | type family (xs :: [a]) ++ (ys :: [a]) :: [a] | ||
30 | type instance '[] ++ ys = ys | ||
31 | type instance (x ': xs) ++ ys = x ': (xs ++ ys) | ||
32 | infixr 5 ++ | ||