{-# LANGUAGE TupleSections, MultiParamTypeClasses, FlexibleInstances, FunctionalDependencies, UndecidableInstances, CPP #-} module Language.LambdaPlaceholders ( CurryingApp(..) , UncurryingApp(..) -- * Example Usage -- $simpleExample ) where infixl 0 .$. class CurryingApp a b e | b a -> e, e b -> a where -- | @foo'.$.'arg@ curries @foo@ the correct amount and composes it with @arg@. -- @arg@ must be of the form @a0 -> ... -> aN -> (z0,...,zN1, a0,z0,...zN1,a1,..., aN,z0,...,zNk)@ -- @foo@ must be of the form @(z0,...,zN1, a0,z0,...zN1,a1,..., aN,z0,...,zNk) -> r@ -- '.$.' has the same fixity as '$'. (.$.) :: a -> b -> e instance CurryingApp a d e => CurryingApp a (b -> d) (b -> e) where (.$.) f g b = f .$. g b #define CURRYING_INST(arg) \ instance CurryingApp (arg -> a0) arg a0 where \ (.$.) = ($) CURRYING_INST((a,b)) CURRYING_INST((a,b,c)) CURRYING_INST((a,b,c,d)) CURRYING_INST((a,b,c,d,e)) CURRYING_INST((a,b,c,d,e,f)) CURRYING_INST((a,b,c,d,e,f,g)) CURRYING_INST((a,b,c,d,e,f,g,h)) CURRYING_INST((a,b,c,d,e,f,g,h,i)) CURRYING_INST((a,b,c,d,e,f,g,h,i,j)) CURRYING_INST((a,b,c,d,e,f,g,h,i,j,k)) CURRYING_INST((a,b,c,d,e,f,g,h,i,j,k,l)) CURRYING_INST((a,b,c,d,e,f,g,h,i,j,k,l,m)) CURRYING_INST((a,b,c,d,e,f,g,h,i,j,k,l,m,n)) CURRYING_INST((a,b,c,d,e,f,g,h,i,j,k,l,m,n,o)) CURRYING_INST((a,b,c,d,e,f,g,h,i,j,k,l,m,n,o,p)) CURRYING_INST((a,b,c,d,e,f,g,h,i,j,k,l,m,n,o,p,q)) CURRYING_INST((a,b,c,d,e,f,g,h,i,j,k,l,m,n,o,p,q,r)) CURRYING_INST((a,b,c,d,e,f,g,h,i,j,k,l,m,n,o,p,q,r,s)) CURRYING_INST((a,b,c,d,e,f,g,h,i,j,k,l,m,n,o,p,q,r,s,t)) CURRYING_INST((a,b,c,d,e,f,g,h,i,j,k,l,m,n,o,p,q,r,s,t,u)) CURRYING_INST((a,b,c,d,e,f,g,h,i,j,k,l,m,n,o,p,q,r,s,t,u,v)) CURRYING_INST((a,b,c,d,e,f,g,h,i,j,k,l,m,n,o,p,q,r,s,t,u,v,w)) CURRYING_INST((a,b,c,d,e,f,g,h,i,j,k,l,m,n,o,p,q,r,s,t,u,v,w,x)) CURRYING_INST((a,b,c,d,e,f,g,h,i,j,k,l,m,n,o,p,q,r,s,t,u,v,w,x,y)) CURRYING_INST((a,b,c,d,e,f,g,h,i,j,k,l,m,n,o,p,q,r,s,t,u,v,w,x,y,z)) #undef CURRYING_INST infixl 0 .@. class UncurryingApp a b e | b a -> e, e b -> a where -- | @foo'.@.'arg@ composes @foo@ with @arg@. -- @arg@ must be of the form @a0 -> ... -> aN -> (z0,...,zN1, a0,z0,...zN1,a1,..., aN,z0,...,zNk)@ -- and @foo@ must be of the form @z0-> ...-> zN1 -> a0 -> ... -> aN -> z0 -> ... -> zNk -> r@ (.@.) :: a -> b -> e instance UncurryingApp a d e => UncurryingApp a (b -> d) (b -> e) where (.@.) f g b = f .@. g b instance UncurryingApp (a -> b -> a0) (a,b) a0 where (.@.) f (a,b) = f a b instance UncurryingApp (a -> b -> c -> a0) (a,b,c) a0 where (.@.) f (a,b,c) = f a b c instance UncurryingApp (a -> b -> c -> d -> a0) (a,b,c,d) a0 where (.@.) f (a,b,c,d) = f a b c d instance UncurryingApp (a -> b -> c -> d -> e -> a0) (a,b,c,d,e) a0 where (.@.) f (a,b,c,d,e) = f a b c d e instance UncurryingApp (a -> b -> c -> d -> e -> f -> a0) (a,b,c,d,e,f) a0 where (.@.) foo (a,b,c,d,e,f) = foo a b c d e f instance UncurryingApp (a -> b -> c -> d -> e -> f -> g -> a0) (a,b,c,d,e,f,g) a0 where (.@.) foo (a,b,c,d,e,f,g) = foo a b c d e f g instance UncurryingApp (a -> b -> c -> d -> e -> f -> g -> h -> a0) (a,b,c,d,e,f,g,h) a0 where (.@.) foo (a,b,c,d,e,f,g,h) = foo a b c d e f g h instance UncurryingApp (a -> b -> c -> d -> e -> f -> g -> h -> i -> a0) (a,b,c,d,e,f,g,h,i) a0 where (.@.) foo (a,b,c,d,e,f,g,h,i) = foo a b c d e f g h i instance UncurryingApp (a -> b -> c -> d -> e -> f -> g -> h -> i -> j -> a0) (a,b,c,d,e,f,g,h,i,j) a0 where (.@.) foo (a,b,c,d,e,f,g,h,i,j) = foo a b c d e f g h i j instance UncurryingApp (a -> b -> c -> d -> e -> f -> g -> h -> i -> j -> k -> a0) (a,b,c,d,e,f,g,h,i,j,k) a0 where (.@.) foo (a,b,c,d,e,f,g,h,i,j,k) = foo a b c d e f g h i j k instance UncurryingApp (a -> b -> c -> d -> e -> f -> g -> h -> i -> j -> k -> l -> a0) (a,b,c,d,e,f,g,h,i,j,k,l) a0 where (.@.) foo (a,b,c,d,e,f,g,h,i,j,k,l) = foo a b c d e f g h i j k l instance UncurryingApp (a -> b -> c -> d -> e -> f -> g -> h -> i -> j -> k -> l -> m -> a0) (a,b,c,d,e,f,g,h,i,j,k,l,m) a0 where (.@.) foo (a,b,c,d,e,f,g,h,i,j,k,l,m) = foo a b c d e f g h i j k l m instance UncurryingApp (a -> b -> c -> d -> e -> f -> g -> h -> i -> j -> k -> l -> m -> o -> a0) (a,b,c,d,e,f,g,h,i,j,k,l,m,o) a0 where (.@.) foo (a,b,c,d,e,f,g,h,i,j,k,l,m,o) = foo a b c d e f g h i j k l m o instance UncurryingApp (a -> b -> c -> d -> e -> f -> g -> h -> i -> j -> k -> l -> m -> o -> p -> a0) (a,b,c,d,e,f,g,h,i,j,k,l,m,o,p) a0 where (.@.) foo (a,b,c,d,e,f,g,h,i,j,k,l,m,o,p) = foo a b c d e f g h i j k l m o p instance UncurryingApp (a -> b -> c -> d -> e -> f -> g -> h -> i -> j -> k -> l -> m -> o -> p -> q -> a0) (a,b,c,d,e,f,g,h,i,j,k,l,m,o,p, q) a0 where (.@.) foo (a,b,c,d,e,f,g,h,i,j,k,l,m,o,p,q) = foo a b c d e f g h i j k l m o p q instance UncurryingApp (a -> b -> c -> d -> e -> f -> g -> h -> i -> j -> k -> l -> m -> o -> p -> q -> r -> a0) (a,b,c,d,e,f,g,h,i,j,k,l,m,o,p,q,r) a0 where (.@.) foo (a,b,c,d,e,f,g,h,i,j,k,l,m,o,p,q,r) = foo a b c d e f g h i j k l m o p q r instance UncurryingApp (a -> b -> c -> d -> e -> f -> g -> h -> i -> j -> k -> l -> m -> o -> p -> q -> r -> s -> a0) (a,b,c,d,e,f,g,h,i,j,k,l,m,o,p,q,r,s) a0 where (.@.) foo (a,b,c,d,e,f,g,h,i,j,k,l,m,o,p,q,r,s) = foo a b c d e f g h i j k l m o p q r s instance UncurryingApp (a -> b -> c -> d -> e -> f -> g -> h -> i -> j -> k -> l -> m -> o -> p -> q -> r -> s -> t -> a0) (a,b,c,d,e,f,g,h,i,j,k,l,m,o,p,q,r,s,t) a0 where (.@.) foo (a,b,c,d,e,f,g,h,i,j,k,l,m,o,p,q,r,s,t) = foo a b c d e f g h i j k l m o p q r s t instance UncurryingApp (a -> b -> c -> d -> e -> f -> g -> h -> i -> j -> k -> l -> m -> o -> p -> q -> r -> s -> t -> u -> a0) (a,b,c,d,e,f,g,h,i,j,k,l,m,o,p,q,r,s,t,u) a0 where (.@.) foo (a,b,c,d,e,f,g,h,i,j,k,l,m,o,p,q,r,s,t,u) = foo a b c d e f g h i j k l m o p q r s t u instance UncurryingApp (a -> b -> c -> d -> e -> f -> g -> h -> i -> j -> k -> l -> m -> o -> p -> q -> r -> s -> t -> u -> v -> a0) (a,b,c,d,e,f,g,h,i,j,k,l,m,o,p,q,r,s,t,u,v) a0 where (.@.) foo (a,b,c,d,e,f,g,h,i,j,k,l,m,o,p,q,r,s,t,u,v) = foo a b c d e f g h i j k l m o p q r s t u v instance UncurryingApp (a -> b -> c -> d -> e -> f -> g -> h -> i -> j -> k -> l -> m -> o -> p -> q -> r -> s -> t -> u -> v -> w -> a0) (a,b,c,d,e,f,g,h,i,j,k,l,m,o,p,q,r,s,t,u,v,w) a0 where (.@.) foo (a,b,c,d,e,f,g,h,i,j,k,l,m,o,p,q,r,s,t,u,v,w) = foo a b c d e f g h i j k l m o p q r s t u v w instance UncurryingApp (a -> b -> c -> d -> e -> f -> g -> h -> i -> j -> k -> l -> m -> o -> p -> q -> r -> s -> t -> u -> v -> w -> x -> a0) (a,b,c,d,e,f,g,h,i,j,k,l,m,o,p,q,r,s,t,u,v,w,x) a0 where (.@.) foo (a,b,c,d,e,f,g,h,i,j,k,l,m,o,p,q,r,s,t,u,v,w,x) = foo a b c d e f g h i j k l m o p q r s t u v w x instance UncurryingApp (a -> b -> c -> d -> e -> f -> g -> h -> i -> j -> k -> l -> m -> o -> p -> q -> r -> s -> t -> u -> v -> w -> x -> y -> a0) (a,b,c,d,e,f,g,h,i,j,k,l,m,o,p,q,r,s,t,u,v,w,x,y) a0 where (.@.) foo (a,b,c,d,e,f,g,h,i,j,k,l,m,o,p,q,r,s,t,u,v,w,x,y) = foo a b c d e f g h i j k l m o p q r s t u v w x y instance UncurryingApp (a -> b -> c -> d -> e -> f -> g -> h -> i -> j -> k -> l -> m -> o -> p -> q -> r -> s -> t -> u -> v -> w -> x -> y -> z -> a0) (a,b,c,d,e,f,g,h,i,j,k,l,m,o,p,q,r,s,t,u,v,w,x,y,z) a0 where (.@.) foo (a,b,c,d,e,f,g,h,i,j,k,l,m,o,p,q,r,s,t,u,v,w,x,y,z) = foo a b c d e f g h i j k l m o p q r s t u v w x y z foo (a,b,c,d,e) = a + b + c + d * c + e curried_foo = foo.$.(2, , 3 , , ) uncurried_foo = curried_foo.@.( , 3 , ) {- $simpleExample @ -- LANGUAGE TupleSections module Main where import Language.LambdaPlaceholders foo (a,b,c,d,e) = a '+' b '+' c '+' d '*' c '+' e curried_foo = foo'.$.'(2, , 3 , , ) uncurried_foo = curried_foo'.@.'( , 3 , ) main = do 'putStrLn' '$' 'show' '$' curried_foo 4 5 @ -}