Loading fizzbuzz.hs 0 → 100644 +46 −0 Original line number Diff line number Diff line import System.Environment type Buzzword = (Integer, String) buzzwords :: [Buzzword] buzzwords = [(3, "Fizz"), (5, "Buzz")] fizzbuzz :: [Either String Integer] fizzbuzz = fizzeval `map` [1 ..] fizzeval :: Integer -> Either String Integer fizzeval x = if null str then Right int else Left str where (int, str) = foldl fizztest (x, "") buzzwords fizztest :: Buzzword -> Buzzword -> Buzzword fizztest (x, xstr) (y, ystr) = if y `divides` x then (x, xstr ++ ystr) else (x, xstr) divides :: Integer -> Integer -> Bool y `divides` x = x `mod` y == 0 -- This place is not a place of honor... no highly esteemed deed is commemorated here... -- nothing valued is here. What is here is dangerous and repulsive to us. -- This message is a warning about the IO Monad. -- The Monad is in a particular location... -- it increases toward the main... the center of danger is here... -- of a particular size and shape, and below us. say :: Either String Integer -> IO () say (Right x) = print x say (Left x) = putStrLn x sayNum :: Maybe Int -> IO () sayNum Nothing = say `foldMap` fizzbuzz sayNum (Just n) = say `foldMap` (take n fizzbuzz) parseArgs :: [String] -> IO (Maybe Int) parseArgs args = if null args then pure Nothing else pure int where int = if null parsed || (not $ null $ snd $ head parsed) then Nothing else Just $ fst $ head parsed where parsed = reads $ head args :: [(Int, String)] main :: IO () main = getArgs >>= parseArgs >>= sayNum Loading
fizzbuzz.hs 0 → 100644 +46 −0 Original line number Diff line number Diff line import System.Environment type Buzzword = (Integer, String) buzzwords :: [Buzzword] buzzwords = [(3, "Fizz"), (5, "Buzz")] fizzbuzz :: [Either String Integer] fizzbuzz = fizzeval `map` [1 ..] fizzeval :: Integer -> Either String Integer fizzeval x = if null str then Right int else Left str where (int, str) = foldl fizztest (x, "") buzzwords fizztest :: Buzzword -> Buzzword -> Buzzword fizztest (x, xstr) (y, ystr) = if y `divides` x then (x, xstr ++ ystr) else (x, xstr) divides :: Integer -> Integer -> Bool y `divides` x = x `mod` y == 0 -- This place is not a place of honor... no highly esteemed deed is commemorated here... -- nothing valued is here. What is here is dangerous and repulsive to us. -- This message is a warning about the IO Monad. -- The Monad is in a particular location... -- it increases toward the main... the center of danger is here... -- of a particular size and shape, and below us. say :: Either String Integer -> IO () say (Right x) = print x say (Left x) = putStrLn x sayNum :: Maybe Int -> IO () sayNum Nothing = say `foldMap` fizzbuzz sayNum (Just n) = say `foldMap` (take n fizzbuzz) parseArgs :: [String] -> IO (Maybe Int) parseArgs args = if null args then pure Nothing else pure int where int = if null parsed || (not $ null $ snd $ head parsed) then Nothing else Just $ fst $ head parsed where parsed = reads $ head args :: [(Int, String)] main :: IO () main = getArgs >>= parseArgs >>= sayNum