source: sizechecking/branches/macs/Lambda.hs @ 19

Last change on this file since 19 was 19, checked in by gobi, 11 years ago

Lambda embedding

File size: 1.4 KB
RevLine 
[19]1{-# LANGUAGE FlexibleContexts,FlexibleInstances #-}
2module Lambda where
3
4import qualified Data.Supply as S
5import qualified Data.Char as C
6
7{-
8 - Lambda calculus beagyazas
9 -}
10class Lambda l where
11    lam   :: (l a -> l b) -> l (a -> b)
12    app   :: l (a -> b) -> l a -> l b
13    const :: Int -> l Int
14
15
16{-
17 - eval interpreter
18 -}
19newtype Q a = Q { unQ :: a }
20instance Lambda Q where
21    const = Q
22    lam a = Q (unQ.a.Q)
23    app a b = Q $ (unQ a) (unQ b)
24
25eval = unQ
26
27instance Num a => Num (Q a) where
28    (Q a) + (Q b) = Q (a+b)
29    (Q a) - (Q b) = Q (a-b)
30    (Q a) * (Q b) = Q (a*b)
31    abs (Q a) = Q (abs a)
32
33
34{-
35 - show interpreter
36 -}
37showVar x = if x>28 
38    then showVar (x `div` 29) . showChar (C.chr $ C.ord 'a' + (x `mod` 29))
39    else showChar $ C.chr $ C.ord 'a' + x
40
41newtype S a = S { unS :: S.Supply Int -> Int -> ShowS }
42instance Lambda S where
43    const a = S (\s p -> flip showsPrec a p)
44    app (S fun) (S arg) = S (\s p -> 
45        let (s1, s2) = S.split2 s
46        in showParen (p>6) $ fun s1 6 . showChar ' ' . arg s2 7)
47    lam fun = S (\s p -> 
48        let (s1, s2) = S.split2 s
49            v        = S.supplyValue s1
50            showV = S $ \_ _ -> showVar v
51        in showParen (p>0) $ showChar 'λ' . showVar v . showChar '.' . unS (fun showV) s2 0)
52
53ast a = do
54    s <- S.newSupply 0 (+1)
55    return $ unS a s 0
56
57printAst a = ast a >>= (\a -> putStrLn $ a "")
58
Note: See TracBrowser for help on using the repository browser.