Skip to content

Instantly share code, notes, and snippets.

@dpwiz
Created April 29, 2014 20:43
Show Gist options
  • Save dpwiz/484737e4ee524100a267 to your computer and use it in GitHub Desktop.
Save dpwiz/484737e4ee524100a267 to your computer and use it in GitHub Desktop.
{-# LANGUAGE TemplateHaskell #-}
module CNth where
import Language.Haskell.TH
import Data.List
cnth :: Int -> Q Exp
cnth n = dotE qs
where
qs = head . reverse . take n . drop 1 $ ads
ads = (inits . repeat) [car, cdr] >>= sequence
car = [| head |]
cdr = [| tail |]
-- Fold expression list with composition.
dotE :: [Q Exp] -> Q Exp
dotE [] = error "dotE: empty list"
dotE [f] = f
dotE (f:g:hs) = dotE ( [| $(f) . $(g) |] : hs )
*CNth> :t $(cnth 42)
<interactive>:1:3-9: Splicing expression
cnth 42 ======> ((((head . tail) . head) . tail) . tail)
$(cnth 42) :: [[c]] -> c
*CNth> :t $(cnth 1)
<interactive>:1:3-8: Splicing expression
cnth 1 ======> head
$(cnth 1) :: [a] -> a
*CNth> :t $(cnth 2)
<interactive>:1:3-8: Splicing expression
cnth 2 ======> tail
$(cnth 2) :: [a] -> [a]
*CNth> :t $(cnth 3)
<interactive>:1:3-8: Splicing expression
cnth 3 ======> (head . head)
$(cnth 3) :: [[c]] -> c
*CNth> :t $(cnth 4)
<interactive>:1:3-8: Splicing expression
cnth 4 ======> (head . tail)
$(cnth 4) :: [c] -> c
*CNth> :t $(cnth 5)
<interactive>:1:3-8: Splicing expression
cnth 5 ======> (tail . head)
$(cnth 5) :: [[a]] -> [a]
*CNth> :t $(cnth 6)
<interactive>:1:3-8: Splicing expression
cnth 6 ======> (tail . tail)
$(cnth 6) :: [a] -> [a]
*CNth> :t $(cnth 7)
<interactive>:1:3-8: Splicing expression
cnth 7 ======> ((head . head) . head)
$(cnth 7) :: [[[c]]] -> c
*CNth> :t $(cnth 8)
<interactive>:1:3-8: Splicing expression
cnth 8 ======> ((head . head) . tail)
$(cnth 8) :: [[c]] -> c
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment