Haskell in the Real World
Upcoming SlideShare
Loading in...5
×
 

Haskell in the Real World

on

  • 2,619 views

A short talk on what makes Functional Programming - and especially Haskell - different....

A short talk on what makes Functional Programming - and especially Haskell - different.

We'll take a quick overview of Haskell's features and coding style, and then work through a short but complete example of using it for a Real World problem.

http://lanyrd.com/2011/geekup-liverpool-may/sdykh/

Statistics

Views

Total Views
2,619
Views on SlideShare
1,777
Embed Views
842

Actions

Likes
0
Downloads
17
Comments
1

5 Embeds 842

http://ontwik.com 672
http://lanyrd.com 162
url_unknown 6
https://lanyrd.com 1
http://ontwik.com.sixxs.org 1

Accessibility

Categories

Upload Details

Uploaded via as Adobe PDF

Usage Rights

© All Rights Reserved

Report content

Flagged as inappropriate Flag as inappropriate
Flag as inappropriate

Select your reason for flagging this presentation as inappropriate.

Cancel
  • Full Name Full Name Comment goes here.
    Are you sure you want to
    Your message goes here
    Processing…
  • Video at http://vimeo.com/24676617
    Are you sure you want to
    Your message goes here
    Processing…
Post Comment
Edit your comment

Haskell in the Real World Haskell in the Real World Presentation Transcript

  • Haskell in the Real World Functional Programming Night Geekup Liverpool, 31st May, 2011 hakim.cassimally@gmail.comhttp://www.fickr.com/photos/jef_saf/3493852795/
  • What makes FP different?● MJD quoting Norvig (on Lisp): ● “big, important features, features like frst-class functions, dynamic access to the symbol table, and automatic storage management.”● gluing functions together● declarative
  • Popular FP languages● Excel● SQL?● Linq (based on Haskells monads)● Lisp → Scheme → Clojure● Strongly Typed FP (Hindley/Milner) ● ML → Ocaml → F# ● Haskell
  • What makes Haskell different?● Purity● Laziness● High Level● Strong Typing● Memory Managed● Modular● Mathematical rigour ● category theory
  • Sounds a bit ivory tower?● http://prog21.dadgum.com/31.html ● Q “When will Haskell fnally go mainstream?” ● A “most of it already has.”
  • Imperative programming● records = [ "one", "two", "three", "four", "five" ] filtered = []; j = 0; for (i = 0; i < length records; i++) { if (records[i] matches “o”) { filtered[j++] = records[i]; } }
  • Imperative programming● records = [ "one", "two", "three", "four", "five" ] filtered = []; j = 0; for (i = 0; i < length records; i++) { if (records[i] matches “o”) { filtered[j++] = records[i]; } }
  • Functional version● filtered = filter (=~ “o”) records
  • Why is this better?● less code. less bugs● no synthetic variables ● i, j, length records● no risk of off-by-one error● intent clear from skimming● intent clear to compiler● parallelize (MapReduce, Hadoop)
  • Why is this better?● fewer codes. fewer bugs● no synthetic variables ● i, j, length records● no risk of off-by-one error● intent clear from skimming● intent clear to compiler● parallelize (MapReduce, Hadoop)
  • Your language has this construct● Perl: my @filtered = grep /o/, @records;● .Net: var filtered = from r in records where r.match(o) select r● Ruby: @filtered = @records.grep /o/● Python: filtered = [x for x in records if re.match(o, x)]● etc.
  • Another example● countCaps = length . filter (isUpper . head) . words > countCaps “Hello there, Fred” 2
  • Real World Haskell● JSON library● barcode reading● database
  • Quizzes● important subsystem of Makinis attention management system● real world (has customers, pays wages)● currently written in Perl● could it be ported to Haskell?
  • Haskell Quiz – proof of concept● full code at: ● https://github.com/ osfameron/geekup-talk-haskell/● overview, to give a favour of programming in Haskell
  • Modelling the quiz
  • Modelling the quiz
  • Modelling the quiz
  • Modelling the quiz2x
  • Modelling the quiz
  • Modelling the quiz1x
  • Quiz tree data types● Quizzes● Sections ● (randomized sections)● Questions
  • Quiz data type● data QuizNode = Quiz Name [QuizNode] | Section Name Score [QuizNode] | RandomSection Name Score Choose [QuizNode] | Question Name Score Answer
  • Quiz data type● data QuizNode = Quiz Name [QuizNode] | Section Name Score [QuizNode] | RandomSection Name Score Choose [QuizNode] | Question Name Score Answer● type Name = String type Score = Int type Choose = Int
  • Quiz data type● data QuizNode = Quiz Name [QuizNode] | Section Name Score [QuizNode] | RandomSection Name Score Choose [QuizNode] | Question Name Score Answer● data Answer = MultiChoice [BoolAnswer] | StringChoice [String]
  • Quiz data type● data QuizNode = Quiz Name [QuizNode] | Section Name Score [QuizNode] | RandomSection Name Score Choose [QuizNode] | Question Name Score Answer● data Answer = MultiChoice [BoolAnswer] | StringChoice [String]● data BoolAnswer = BoolAnswer Bool String
  • Quiz data typequiz,geo,pop :: QuizNodequiz = Quiz “General Knowledge Quiz” [ pop, geo ]geo = RandomSection “Geography” 40 2 [ Question “What is the capital of England?” 2 $ StringChoice [“London”], Question “What is the capital of France?” 2 $ StringChoice [“Paris”], Question “What is the capital of Finland?” 2 $ StringChoice [“Helsinki”], Question “What is the capital of Italy?” 2 $ StringChoice [“Rome”, “Roma”], ]
  • Quiz data typequiz,geo,pop :: QuizNodequiz = Quiz “General Knowledge Quiz” [ pop, geo ]geo = RandomSection “Geography” 40 2 [ Question “What is the capital of England?” 2 $ StringChoice [“London”], Question “What is the capital of France?” 2 $ StringChoice [“Paris”], Question “What is the capital of Finland?” 2 $ StringChoice [“Helsinki”], Question “What is the capital of Italy?” 2 $ StringChoice [“Rome”, “Roma”], ]
  • Quiz data typequiz,geo,pop :: QuizNodequiz = Quiz “General Knowledge Quiz” [ pop, geo ]geo = RandomSection “Geography” 40 2 [ Question “What is the capital of England?” 2 $ StringChoice [“London”], Question “What is the capital of France?” 2 $ StringChoice [“Paris”], Question “What is the capital of Finland?” 2 $ StringChoice [“Helsinki”], Question “What is the capital of Italy?” 2 $ StringChoice [“Rome”, “Roma”], ]
  • Quiz data typepop = Section “Pop music” 60 [ Question “Which of these are Beatles?” 5 $ MultiChoice [ y “John”, y “Paul”, y “George”, y “Ringo”, n “Bob”, n “Jason” ], ...
  • Quiz data typepop = Section “Pop music” 60 [ Question “Which of these are Beatles?” 5 $ MultiChoice [ BoolAnswer True “John”, BoolAnswer True “Paul”, BoolAnswer True “George”, BoolAnswer True “Ringo”, BoolAnswer False “Bob”, BoolAnswer False “Jason” ], ...
  • Quiz data typepop = Section “Pop music” 60 [ Question “Which of these are Beatles?” 5 $ MultiChoice [ y “John”, y “Paul”, y “George”, y “Ringo”, n “Bob”, n “Jason” ], ...y,n :: String -> BoolAnswery = BoolAnswer Truen = BoolAnswer False
  • Stamping the quiz1x 2x
  • Stamping the quiz1x 2x
  • Stamping the quiz stamp :: QuizNode → ...1x 2x
  • Stamping the quiz stamp :: QuizNode → QuizNode?1x 2x
  • Functions● increment :: Num → Num ● increment 4 => 5 ● increment 10 => 11
  • Functions● increment :: Num → Num ● increment 4 => 5 ● increment 10 => 11
  • Functions● increment :: Num → Num ● increment 4 => 5 ● increment 10 => 11
  • Functions● increment :: Num → Num● increment x = x+1
  • Functionslet x = 42 addx :: Num → Num add y = x + y
  • Functions (cannotlet x = 42 change!) addx :: Num → Num add y = x + y
  • Functionslet x = 42 addx :: Num → Num add y = x + y
  • Stamping the quiz stamp :: QuizNode → QuizNode?1x 2x
  • Stamping the quiz stamp :: QuizNode → QuizNode?1x 2x
  • Stamping the quiz stamp :: QuizNode → IO QuizNode1x 2x
  • Monads● Useful data-structure● Lets us model various thing... ● including IO in a pure language● Concept is a little confusing● Using them is (mostly) not too bad.
  • Stamping the quiz stamp :: QuizNode → IO QuizNode
  • Stamping the quiz stamp :: QuizNode → IO QuizNode1x 2x
  • Stamping the quiz stamp :: QuizNode → IO QuizNode1x 2x
  • Stamping the quiz stamp :: QuizNode → IO QuizNode
  • Stamping the quiz stamp :: QuizNode → IO QuizNode
  • The stamp functionstamp :: QuizNode -> IO QuizNodestamp q@(Question _ _ _) = return qstamp (Quiz s ns) = Quiz s <$> mapM stamp nsstamp (Section s i ns) = Section s i <$> mapM stamp nsstamp (RandomSection s i r ns) = do selected <- pickN r ns Section s i <$> mapM stamp selected
  • The stamp functionstamp :: QuizNode -> IO QuizNodestamp q@(Question _ _ _) = return qstamp (Quiz s ns) = Quiz s <$> mapM stamp nsstamp (Section s i ns) = Section s i <$> mapM stamp nsstamp (RandomSection s i r ns) = do selected <- pickN r ns Section s i <$> mapM stamp selected
  • The stamp function map stamp nsstamp :: QuizNode -> IO QuizNode – “stamp all the child nodes instamp q@(Question _ _ _) = return q turn”stamp (Quiz s ns) = Quiz s <$> mapM stamp nsstamp (Section s i ns) = Section s i <$> mapM stamp nsstamp (RandomSection s i r ns) = do selected <- pickN r ns Section s i <$> mapM stamp selected
  • The stamp functionstamp :: QuizNode -> IO QuizNodestamp q@(Question _ _ _) = return qstamp (Quiz s ns) = Quiz s <$> mapM stamp nsstamp (Section s i ns) = Section s i <$> mapM stamp nsstamp (RandomSection s i r ns) = do selected <- pickN r ns Section s i <$> mapM stamp selected
  • The stamp functionstamp :: QuizNode -> IO QuizNodestamp q@(Question _ _ _) = return qstamp (Quiz s ns) = Quiz s <$> mapM stamp nsstamp (Section s i ns) = Section s i <$> mapM stamp nsstamp (RandomSection s i r ns) = do selected <- pickN r ns Section s i <$> mapM stamp selected1x
  • Taking the quiz!● takeNode :: QuizNode -> IO CompletedNode● printQuestion :: QuizNode -> IO ()● showBoolTextAnswers :: [BoolAnswer] -> String● checkAnswer :: String -> Answer -> Bool
  • Taking the quiz!● takeNode :: QuizNode -> IO CompletedNode● printQuestion :: QuizNode -> IO ()● showBoolTextAnswers :: [BoolAnswer] -> String● checkAnswer :: String -> Answer -> Bool
  • Taking the quiz!● takeNode :: QuizNode -> IO CompletedNode● printQuestion :: QuizNode -> IO ()● showBoolTextAnswers :: [BoolAnswer] -> String● checkAnswer :: String -> Answer -> Bool
  • Taking the quiz!● takeNode :: QuizNode -> IO CompletedNode● printQuestion :: QuizNode -> IO ()● showBoolTextAnswers :: [BoolAnswer] -> String● checkAnswer :: String -> Answer -> Bool
  • takeNodetakeNode node@(Question s i a) = do printQuestion node ans <- getLine let correct = checkAnswer ans a let score = if correct then (i,i) else (0,i) putStrLn $ if correct then “Correct!” else “Wrong!” return $ CompletedNode ans score [] node
  • mainmain :: IO ()main = stamp quiz >>= takeQuiz Function, not entrypoint
  • mainmain :: IO ()main = stamp quiz >>= takeQuiz Live Demo!
  • Should you go Haskell?● Power● Speed? ● can be faster than C (supercompilation) ● can be tricky to optimize● Jobs? ● In NorthWestUK?● Libraries & Tools ● Haskell Platform. Hackage. Cabal
  • Should you learn Haskell?● Powerful● Interesting techniques● … and ways of thinking about problems● Ready for future shift to FP● … possibly in your own language
  • Thank you! Questions? ● full code at: ● https://github.com/ osfameron/geekup-talk-haskell/ ● hakim.cassimally@gmail.comhttp://www.fickr.com/photos/jef_saf/3493852795/