fork download
  1. import Control.Monad.Trans.State
  2. import Data.List (intercalate)
  3. import Control.Monad.IO.Class (liftIO)
  4.  
  5. type TodoState a = StateT [Todo] IO a
  6. type Category = String
  7.  
  8. data Todo = Todo { text :: String
  9. , categories :: [Category]
  10. } deriving (Show)
  11.  
  12. addItem :: String -> [Category] -> TodoState ()
  13. addItem txt cs = modify (Todo txt cs:)
  14.  
  15. updateItem :: String -> String -> TodoState ()
  16. updateItem old new = modify (map (\x -> if text x == old then x {text = new} else x))
  17.  
  18. viewList :: [Category] -> TodoState ()
  19. viewList cs = do list <- get
  20. liftIO $ do
  21. putStrLn $ "# " ++ intercalate " & " cs
  22. mapM_ (putStrLn . ("- " ++) . text) $ filterCategory cs list
  23. putStr "\n"
  24.  
  25. filterCategory :: [Category] -> [Todo] -> [Todo]
  26. filterCategory cs = filter (any (`elem` cs) . categories)
  27.  
  28. runTodo :: TodoState () -> IO ()
  29. runTodo = flip evalStateT []
  30.  
  31. main :: IO ()
  32. main = runTodo $ do
  33. addItem "Go to work" ["Programming"]
  34. addItem "Create Sine Waves in C" ["Music", "Programming"]
  35. addItem "Play my synth" ["Music"]
  36. viewList ["Music"]
  37. updateItem "Create Sine Waves in C" "Create Sine Waves in Python"
  38. viewList ["Programming"]
  39. viewList ["Programming", "Music"]
  40.  
Success #stdin #stdout 0s 4556KB
stdin
Standard input is empty
stdout
# Music
- Play my synth
- Create Sine Waves in C

# Programming
- Create Sine Waves in Python
- Go to work

# Programming & Music
- Play my synth
- Create Sine Waves in Python
- Go to work