data Parser c a = Parser ([c] -> Error (a,[c])) data Error a = Valid a | Error String deriving Show instance Monad Error where Valid a >>= f = f a Error s >>= f = Error s --Valid f <*> Valid a = Valid (f a) --Error s <*> _ = Error s --_ <*> Error s = Error s --return = Valid instance Functor Error where fmap f (Error s) = Error s fmap f (Valid a) = Valid (f a) instance Applicative Error where pure = Valid instance Functor (Parser c) where fmap :: (a->b) -> Parser c a -> Parser c b fmap f (Parser g) = Parser h where h s = g s >>= (\(parsed,rest) -> pure (f parsed, rest)) linkNeighbours :: [a] -> [(a,a)] linkNeighbours (head:y:xs) = (head,y):(linkNeighbours' head (y:xs)) linkNeighbours' :: a -> [a] -> [(a,a)] linkNeighbours' head (x:y:xs) = (x,y):(linkNeighbours' head (y:xs)) linkNeighbours' head [x] = [(x,head)] polyArea :: [(Double,Double)] -> Double polyArea = (0.5*) . sum . map (\((x1,y1),(x2,y2)) -> (y1+y2)*(x1-x2)) . linkNeighbours svgPathToPolygon :: Parser Char [(Double,Double)] svgPathToPolygon = symbol 'm' 'm' symbol :: (Show s,Eq s) =>s -> a -> Parser s a symbol c a = Parser f where f [] = Error "No symbol" f (s:ss) = if s==c then Valid (a,ss) else Error ("Expected "++show c) --The are if correct should be 4233.8898623135065 <= (maxX-minX)(maxY-minY) = (704.94638+38.986565)(22.381667+55.33534) =