Sha256: aabc632c50be3e4e68ecca44f1612f1fa88d4dfab52cdabeaea7d9399b0e26cb

Contents?: true

Size: 1.61 KB

Versions: 396

Compression:

Stored size: 1.61 KB

Contents

module POV (fromPOV, tracePathBetween) where

import Data.Maybe(listToMaybe, mapMaybe)
import Data.Tree(Tree(Node), rootLabel, subForest)

data Crumb a = Crumb a [Tree a] [Tree a] deriving (Show, Eq)
data Zipper a = Zipper { node :: Tree a, path :: [Crumb a] }

fromPOV :: Eq a => a -> Tree a -> Maybe (Tree a)
fromPOV x = fmap reparent . findLoc x . rootZipper

tracePathBetween :: Eq a => a -> a -> Tree a -> Maybe [a]
tracePathBetween from to g =
    fromPOV from g |>= rootZipper >>= findLoc to |>= trail |>= map rootLabel |>= (++ [to])

reparent :: Eq a => Zipper a -> Tree a
reparent (Zipper g []) = g
reparent (Zipper g (c:cs)) = Node (rootLabel g) $ subForest g ++ [reparented]
    where reparented = reparent (Zipper (crumbToTree c) cs)

down :: Zipper a -> Maybe (Zipper a)
down (Zipper (Node v (k : kids)) crumbs) = Just $ Zipper k $ Crumb v [] kids : crumbs
down _ = Nothing

right :: Zipper a -> Maybe (Zipper a)
right (Zipper here (Crumb v lefts (r : rights) : cs)) = Just $ Zipper r $ shifted : cs
    where shifted = Crumb v (lefts ++ [here]) rights
right _ = Nothing

findLoc :: Eq a => a -> Zipper a -> Maybe (Zipper a)
findLoc x loc
    | x == (rootLabel . node $ loc) = Just loc
    | otherwise = listToMaybe $ mapMaybe look [down, right]
    where look dir = dir loc >>= findLoc x

trail :: Zipper a -> [Tree a]
trail = reverse . map crumbToTree . path

crumbToTree :: Crumb a -> Tree a
crumbToTree (Crumb x lefts rights) = Node x (lefts ++ rights)

rootZipper :: Tree a -> Zipper a
rootZipper g = Zipper g []

infixl 1 |>= -- allow pure and monadic functions in pipe.
(|>=) :: Functor f => f a -> (a -> b) -> f b
(|>=) = flip fmap

Version data entries

396 entries across 396 versions & 1 rubygems

Version Path
trackler-2.2.1.180 tracks/haskell/exercises/pov/examples/success-standard/src/POV.hs
trackler-2.2.1.179 tracks/haskell/exercises/pov/examples/success-standard/src/POV.hs
trackler-2.2.1.178 tracks/haskell/exercises/pov/examples/success-standard/src/POV.hs
trackler-2.2.1.177 tracks/haskell/exercises/pov/examples/success-standard/src/POV.hs
trackler-2.2.1.176 tracks/haskell/exercises/pov/examples/success-standard/src/POV.hs
trackler-2.2.1.175 tracks/haskell/exercises/pov/examples/success-standard/src/POV.hs
trackler-2.2.1.174 tracks/haskell/exercises/pov/examples/success-standard/src/POV.hs
trackler-2.2.1.173 tracks/haskell/exercises/pov/examples/success-standard/src/POV.hs
trackler-2.2.1.172 tracks/haskell/exercises/pov/examples/success-standard/src/POV.hs
trackler-2.2.1.171 tracks/haskell/exercises/pov/examples/success-standard/src/POV.hs
trackler-2.2.1.170 tracks/haskell/exercises/pov/examples/success-standard/src/POV.hs
trackler-2.2.1.169 tracks/haskell/exercises/pov/examples/success-standard/src/POV.hs
trackler-2.2.1.167 tracks/haskell/exercises/pov/examples/success-standard/src/POV.hs
trackler-2.2.1.166 tracks/haskell/exercises/pov/examples/success-standard/src/POV.hs
trackler-2.2.1.165 tracks/haskell/exercises/pov/examples/success-standard/src/POV.hs
trackler-2.2.1.164 tracks/haskell/exercises/pov/examples/success-standard/src/POV.hs
trackler-2.2.1.163 tracks/haskell/exercises/pov/examples/success-standard/src/POV.hs
trackler-2.2.1.162 tracks/haskell/exercises/pov/examples/success-standard/src/POV.hs
trackler-2.2.1.161 tracks/haskell/exercises/pov/examples/success-standard/src/POV.hs
trackler-2.2.1.160 tracks/haskell/exercises/pov/examples/success-standard/src/POV.hs