SlideShare a Scribd company logo
1 of 251
Download to read offline
Haskell
A Whirlwind Tour
     William Taysom
           2011
Haskell
Haskell

Who?

What?

When?

Where?

Why?

How?
Haskell

Who?

What?

When?

Where?

Why?

How?
Why?




       Aesthetics
Why? Aesthetics
“We provided DARPA with a copy of our prototype
implemented in Haskell without explaining that it was
a program, and based on preconceptions from their
past experience, they had studied the program under
the assumption that it was a mixture of requirements
specification and top level design. They were
convinced it was incomplete because it did not address
issues such as data structure design and execution
order.”
                                          — Paul Hudak
Why? Aesthetics



“Take Lisp: you know it's the most beautiful language
in the world. At least up until Haskell came along.”

                                         — Larry Wall
Why? Aesthetics



“Reading Haskell is like reading poetry.
Writing Haskell is like writing poetry.”

                                           — Oliver Steele
Why? Aesthetics


“I also have interest in Haskell, but my brain just
explodes every time I read a Haskell program bigger
than ten lines.”

                                             — Matz
Why? Aesthetics



“The biggest advantage of Haskell to me is that it helps
me write better programs in other languages.”

                                — Tenerife Skunkworks
Why? Aesthetics


.NET       LINQ

Python     List Comprehensions

Java       Generics

JavaScript jQuery
Why?




       Pragmatics
Why? Pragmatics


Platform    Compiler   Debugger     Profiler Testing

Libraries   Network      Graphics            Hackage

Community Books        Documentation         Hoogle
Why? Pragmatics


Platform    Compiler   Debugger     Profiler Testing

Libraries   Network      Graphics            Hackage

Community Books        Documentation         Hoogle
Why? Pragmatics
        Hoogle
Why? Pragmatics
        Hoogle
Why? Pragmatics


Platform    Compiler   Debugger     Profiler Testing

Libraries   Network      Graphics            Hackage

Community Books        Documentation         Hoogle
Why? Pragmatics


Platform    Compiler   Debugger     Profiler Testing

Libraries   Network      Graphics            Hackage

Community Books        Documentation         Hoogle
How?

       GHC
   Documentation
     Libraries
       Cabal
      Hackage
Why? Pragmatics


Platform    Compiler   Debugger     Profiler Testing

Libraries   Network      Graphics            Hackage

Community Books        Documentation         Hoogle
Why? Pragmatics
Why? Pragmatics
Why? Pragmatics

“A programming language must be considered in the
context of its community, and Haskell has an
exemplary one. I have come to believe, however, that
this polite exterior conceals a deep and consuming
madness.”

                                       — Avdi Grimm
Why?




       Performance
Why? Performance
The Computer Language Benchmarks Game
Why? Performance



             Web Server
   Pong benchmark, extra large instance, requests/second
Why? Performance



             Web Server
   Pong benchmark, extra large instance, requests/second
Why?


        Aesthetics
        Pragmatics
       Performance
Haskell

Who?

What?

When?

Where?

Why?     Aesthetics   Pragmatics   Performance

How?
Haskell

Who?

What?

When?

Where?

Why?     Aesthetics   Pragmatics   Performance

How?
Who? When? Where?




    September 1987
Who? When? Where?

   Portland, Oregon
Who? When? Where?



Functional Programming
Languages and Computer
Architecture Conference
Who? When? Where?


   A Dozen Purely
 Functional Languages
Who? When? Where?




     All Similar
Who? When? Where?
     Committee Formed
Who? When? Where?
     Committee Formed
Provide faster communication of new
ideas.

Stable foundation for real application
development.

Vehicle through which others would be
encouraged to use functional languages.
Who? When? Where?

Haskell Report
April 1st 1990

“You know, Haskell
actually never liked the
name Haskell.”

            — Mary Curry
Who? When? Where?


          2002

Revised Haskell 98 Report
Who? When? Where?


       2010

      Haskell'
Haskell

Who?    Research     Wadler   Hudak   Peyton-Jones

What?

When?   1987         1990     2002    Now

Where? Portland        Glasgow        Microsoft

Why?    Aesthetics     Pragmatics     Performance

How?
Haskell

Who?    Research     Wadler   Hudak   Peyton-Jones

What?

When?   1987         1990     2002    Now

Where? Portland        Glasgow        Microsoft

Why?    Aesthetics     Pragmatics     Performance

How?
What?


A non-strict, purely
functional programming
language with strong,
static type inference.
What?


A non-strict, purely
functional programming
language with strong,
static type inference.
What? Programming

Source Code

Formal, Textural Syntax

Static & Runtime Semantics

Data, Variables, Lexical Scope

Interpreter, Compiler
What?


A non-strict, purely
functional programming
language with strong,
static type inference.
What?


A non-strict, purely
functional programming
language with strong,
static type inference.
What? Functional




    (Not Imperative)
What? Functional

Imperative   Statements Executed Step-by-step
What? Functional

Imperative   Statements Executed Step-by-step
             Modifying State
What? Functional

Imperative   Statements Executed Step-by-step
             Modifying State
             Turing Machine
What? Functional

Imperative   Statements Executed Step-by-step
             Modifying State
             Von Neumann Architecture
What? Functional

Imperative   Statements Executed Step-by-step
             Modifying State
             Von Neumann Architecture


Functional   Expressions Recursively Simplified
What? Functional

Imperative   Statements Executed Step-by-step
             Modifying State
             Von Neumann Architecture


Functional   Expressions Recursively Simplified
             Reduced Value
What? Functional

Imperative   Statements Executed Step-by-step
             Modifying State
             Von Neumann Architecture


Functional   Expressions Recursively Simplified
             Reduced Value
             Lambda Calculus
What? Functional

Imperative   Statements Executed Step-by-step
             Modifying State
             Von Neumann Architecture


Functional   Expressions Recursively Simplified
             Reduced Value
             Lambda Calculus
What? Functional

Imperative   Statements Executed Step-by-step
             Modifying State
             Von Neumann Architecture


Functional   Expressions Recursively Simplified
             Reduced Value
             Lambda Calculus
What?


A non-strict, purely
functional programming
language with strong,
static type inference.
What?


A non-strict, purely
functional programming
language with strong,
static type inference.
What? Pure




    (No Side Effects)
What? Pure


    Immutable Only
What? Pure




Referential Transparency
What? Pure


    Functions always
  return the same value.

     If v = f x, then you can
    always replace f x with v.
What? Pure


    Functions always
  return the same value.

   If v equals f x, then you can
    always replace f x with v.
What?


A non-strict, purely
functional programming
language with strong,
static type inference.
What?


A non-strict, purely
functional programming
language with strong,
static type inference.
What? Non-strict


        Be lazy.
What? Non-strict


         Be lazy.

 Ignore evaluation order.
Wait...
if everything is
immutable and there
 are no side effects
and evaluation is lazy,
then how the hell do
  you do anything?
MONADS
 Bring your own Semicolon
What? Monads
What? Monads
What? Monads
What? Monads
What? Monads
What? Monads



“Haskell is the world's finest
imperative programming language.”

                            — Simon Peyton-Jones
What? Monads



“Haskell is the only language I know with
first-class support for imperative programming.”

                                             — SamB
What? Monads


“Haskell has no preferred imperative semantics, and
the monad just lets you swap out the semantics
according to your needs.”

                                     — Jared Updike
What?


A non-strict, purely
functional programming
language with strong,
static type inference.
What?


A non-strict, purely
functional programming
language with strong,
static type inference.
What? Types


       Strong
        Static
      Inference
What? Types


       Strong
        Static
      Inference
What? Strong Types

    Runtime values
      have types.
What? Strong Types

    Runtime values
      have types.
      like Java and Ruby
     unlike C and Assembly
          (Not Weak)
What? Types


       Strong
        Static
      Inference
What? Types


       Strong
        Static
      Inference
What? Static Types

 Source code expressions
       have types.
What? Static Types

 Source code expressions
       have types.
         like C and Java
   unlike Ruby and JavaScript
         (Not Dynamic)
What? Types


       Strong
        Static
      Inference
What? Types


       Strong
        Static
      Inference
What? Type Inference

Automatically determines
   types of variables.
What? Type Inference

Automatically determines
   types of variables.
       like C# and Go
      unlike C and Java
       (Not Manifest)
You don’t need to
 type the type!
SYNERGY
 Purity means types tell you a lot.
What? Type Purity

     No side effects
         mean,
What? Type Purity

     No side effects
         mean,
  argument and return
    types limit what
   a function can do.
What? Type Purity


“Haskell is so strict about type safety that randomly
generated snippets of code that successfully type check
are likely to do something useful, even if you've no idea
what that useful thing is.”

                                                — sigfpe
What? Type Purity


“Since when does "it compiles" equate to "it will run
(correctly)"? We're talking about C, after all, not
Haskell.”

                                         — Sean Russell
What? Types


       Strong
        Static
      Inference
What?


A non-strict, purely
functional programming
language with strong,
static type inference.
What?


A non-strict, purely
functional programming
language with strong,
static type inference.
Haskell

Who?    Research     Wadler   Hudak    Peyton-Jones

What?   Non-strict   Purely Functional Static Types

When?   1987         1990     2002     Now

Where? Portland         Glasgow        Microsoft

Why?    Aesthetics      Pragmatics     Performance

How?
Haskell

Who?    Research     Wadler   Hudak    Peyton-Jones

What?   Non-strict   Purely Functional Static Types

When?   1987         1990     2002     Now

Where? Portland         Glasgow        Microsoft

Why?    Aesthetics      Pragmatics     Performance

How?
How?


       Just Download
         and Install
        the Platform
How?


       Just Download
         and Install
        the Platform
Glorious Glasgow
Haskell Compilation
      System
GHC


Compiler      ghc

Interactive   ghci

Scripts       runghc
GHC


Compiler      ghc

Interactive   ghci

Scripts       runghc
Haskell

Who?    Research     Wadler   Hudak    Peyton-Jones

What?   Non-strict   Purely Functional Static Types

When?   1987         1990     2002     Now

Where? Portland         Glasgow        Microsoft

Why?    Aesthetics      Pragmatics     Performance

How?    Platform        Hoogle         Hackage
Haskell

Who?    Research     Wadler   Hudak    Peyton-Jones

What?   Non-strict   Purely Functional Static Types

When?   1987         1990     2002     Now

Where? Portland         Glasgow        Microsoft

Why?    Aesthetics      Pragmatics     Performance

How?    Platform        Hoogle         Hackage
Example
┼ $




      Example
$ ghci
$ ghci
GHCi, version 7.0.2: http://
www.haskell.org/ghc/ :? for help
Loading package ghc-prim ... linking ...
done.
Loading package integer-gmp ...
linking ... done.
Loading package base ... linking ...
done.
Loading package ffi-1.0 ... linking ...
done.
ghci>
$ ghci
GHCi, version 7.0.2: http://
www.haskell.org/ghc/ :? for help
Loading package ghc-prim ... linking ...
done.
Loading package integer-gmp ...
linking ... done.
Loading package base ... linking ...
done.
Loading package ffi-1.0 ... linking ...
done.
ghci> "hello, world"
$ ghci
GHCi, version 7.0.2: http://
www.haskell.org/ghc/ :? for help
Loading package ghc-prim ... linking ...
done.
Loading package integer-gmp ...
linking ... done.
Loading package base ... linking ...
done.
Loading package ffi-1.0 ... linking ...
done.
ghci> "hello, world"
"hello, world"
ghci>
"hello, world"
ghci>
"hello, world"
ghci> 6 * 9
"hello, world"
ghci> 6 * 9
42
ghci>
"hello, world"
ghci> 6 * 9
42
ghci> [1, 2, 3]
"hello, world"
ghci> 6 * 9
42
ghci> [1, 2, 3]
[1,2,3]
ghci>
"hello, world"
ghci> 6 * 9
42
ghci> [1, 2, 3]
[1,2,3]
ghci> it
"hello, world"
ghci> 6 * 9
42
ghci> [1, 2, 3]
[1,2,3]
ghci> it
[1,2,3]
ghci>
"hello, world"
ghci> 6 * 9
42
ghci> [1, 2, 3]
[1,2,3] application is so important in Haskell that
 “Function
ghci> it it using the quietest possible syntax:
 we denote
[1,2,3]at all.”
 nothing
ghci> reverse it
                               — Simon Peyton-Jones
“Function application is so important in Haskell that
we denote it using the quietest possible syntax:
nothing at all.”

                                — Simon Peyton-Jones
"hello, world"
ghci> 6 * 9
42
ghci> [1, 2, 3]
[1,2,3] application is so important in Haskell that
 “Function
ghci> it it using the quietest possible syntax:
 we denote
[1,2,3]at all.”
 nothing
ghci> reverse it
                               — Simon Peyton-Jones
"hello, world"
ghci> 6 * 9
42
ghci> [1, 2, 3]
[1,2,3]
ghci> it
[1,2,3]
ghci> reverse it
[3,2,1]
ghci>
[3,2,1]
ghci>
[3,2,1]
ghci> let xs = [1..100]
[3,2,1]
ghci> let xs = [1..100]
ghci>
[3,2,1]
ghci> let xs = [1..100]
ghci> xs
[3,2,1]
ghci> let xs = [1..100]
ghci> xs
[1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,1
7,18,19,20,21,22,23,24,25,26,27,28,29,30,
31,32,33,34,35,36,37,38,39,40,41,42,43,44
,45,46,47,48,49,50,51,52,53,54,55,56,57,5
8,59,60,61,62,63,64,65,66,67,68,69,70,71,
72,73,74,75,76,77,78,79,80,81,82,83,84,85
,86,87,88,89,90,91,92,93,94,95,96,97,98,9
9,100]
ghci>
[3,2,1]
ghci> let xs = [1..100]
ghci> xs
[1,2,⋯,99,100]
ghci>
[3,2,1]
ghci> let xs = [1..100]
ghci> xs
[1,2,⋯,99,100]
ghci> [x | x <- xs, x > 21]
[3,2,1]
ghci> let xs = [1..100]
ghci> xs
[1,2,⋯,99,100]
ghci> [x | x <- xs, x > 21]
[22,23,24,25,26,27,28,29,30,31,32,33,34,3
5,36,37,38,39,40,41,42,43,44,45,46,47,48,
49,50,51,52,53,54,55,56,57,58,59,60,61,62
,63,64,65,66,67,68,69,70,71,72,73,74,75,7
6,77,78,79,80,81,82,83,84,85,86,87,88,89,
90,91,92,93,94,95,96,97,98,99,100]
ghci>
[3,2,1]
ghci> let xs = [1..100]
ghci> xs
[1,2,⋯,99,100]
ghci> [x | x <- xs, x > 21]
[22,23,⋯,99,100]
ghci>
[3,2,1]
ghci> let xs = [1..100]
ghci> xs
[1,2,⋯,99,100]
ghci> [x | x <- xs, x > 21]
[22,23,⋯,99,100]
ghci> filter (> 21) xs
[3,2,1]
ghci> let xs = [1..100]
ghci> xs
[1,2,⋯,99,100]
ghci> [x | x <- xs, x > 21]
[22,23,⋯,99,100]
ghci> filter (> 21) xs
[22,23,⋯,99,100]
ghci>
[3,2,1]
ghci> let xs = [1..100]
ghci> xs
[1,2,⋯,99,100]
ghci> [x | x <- xs, x > 21]
[22,23,⋯,99,100]
ghci> filter (> 21) xs
[22,23,⋯,99,100]
ghci> filter (x -> x > 21) xs
[3,2,1]
ghci> let xs = [1..100]
ghci> xs
[1,2,⋯,99,100]
ghci> [x | x <- xs, x > 21]
[22,23,⋯,99,100]

           TMTOWTDI
ghci> filter (> 21) xs
[22,23,⋯,99,100]
ghci> filter (x -> x > 21) xs
[22,23,⋯,99,100]
ghci>
TMTOWTDI
The Evolution of a
Haskell Programmer
1.    Freshman                13. Continuation-passing
2.    Sophomore               14. Boy Scout
3.    Junior (Peano)          15. Combinatory
4.    Junior (Ban n+k)        16. List-encoding
5.    Senior (Leans Right)    17. Interpretive
6.    Senior (Leans Left)     18. Static
7.    Senior (Leans Around)   19. Beginning Graduate
8.    Memoizing               20. Origamist
9.    Points-free             21. Cartesianally-inclined
10.   Iterative               22. Ph.D.
11.   Iterative one-liner     23. Post-doc
12.   Accumulating            24. Tenured Professor
TMTOWTDI
[3,2,1]
ghci> let xs = [1..100]
ghci> xs
[1,2,⋯,99,100]
ghci> [x | x <- xs, x > 21]
[22,23,⋯,99,100]

          TMTOWTDI
ghci> filter (> 21) xs
[22,23,⋯,99,100]
ghci> filter (x -> x > 21) xs
[22,23,⋯,99,100]
ghci>
[22,23,⋯,99,100]
ghci>
[22,23,⋯,99,100]
ghci> let divides = x y -> rem y x == 0
[22,23,⋯,99,100]
ghci> let divides = x y -> rem y x == 0
ghci>
[22,23,⋯,99,100]
ghci> let divides = x y -> rem y x == 0
ghci> let divides x y = rem y x == 0
[22,23,⋯,99,100]
ghci> let divides = x y -> rem y x == 0
ghci> let divides x y = rem y x == 0
ghci>
[22,23,⋯,99,100]
ghci> let divides = x y -> rem y x == 0
ghci> let divides x y = rem y x == 0
ghci> divides 3 12
[22,23,⋯,99,100]
ghci> let divides = x y -> rem y x == 0
ghci> let divides x y = rem y x == 0
ghci> divides 3 12
True
ghci>
[22,23,⋯,99,100]
ghci> let divides = x y -> rem y x == 0
ghci> let divides x y = rem y x == 0
ghci> divides 3 12
True
ghci> 3 `divides` 12
[22,23,⋯,99,100]
ghci> let divides = x y -> rem y x == 0
ghci> let divides x y = rem y x == 0
ghci> divides 3 12
True
ghci> 3 `divides` 12
True
ghci>
[22,23,⋯,99,100]
ghci> let divides = x y -> rem y x == 0
ghci> let divides x y = rem y x == 0
ghci> divides 3 12
True
ghci> 3 `divides` 12
True
ghci> let divisors x = [d | d <- [1..x],
d `divides` x]
[22,23,⋯,99,100]
ghci> let divides = x y -> rem y x == 0
ghci> let divides x y = rem y x == 0
ghci> divides 3 12
True
ghci> 3 `divides` 12
True
ghci> let divisors x = [d | d <- [1..x],
d `divides` x]
ghci>
[22,23,⋯,99,100]
ghci> let divides = x y -> rem y x == 0
ghci> let divides x y = rem y x == 0
ghci> divides 3 12
True
ghci> 3 `divides` 12
True
ghci> let divisors x = [d | d <- [1..x],
d `divides` x]
ghci> divisors 100
[22,23,⋯,99,100]
ghci> let divides = x y -> rem y x == 0
ghci> let divides x y = rem y x == 0
ghci> divides 3 12
True
ghci> 3 `divides` 12
True
         Fundamentals
ghci> let divisors x = [d | d <- [1..x],
d `divides` x]
ghci> divisors 100
[1,2,4,5,10,20,25,50,100]
ghci>
Fundamentals
Data Declaration

data Color = Red | Green | Blue
Variables

red = Red
-- Lower case for variable and upper case for
constructor.

nan = 0 / 0
-- Variables stand for values. They do not label
locations.
-- Don't need let because we aren't at GHCi.
-- Declarations go at top-level, not expressions.
(Like Java, unlike Ruby.)
Functions

hue Red = 0
hue Green = 120
hue Blue = 240
Lambda & Case

hue = c -> case c of
 Red    -> 0
 Green -> 120
 Blue -> 240
Pattern Wildcard

isRed Red = True
isRed _ = False
Boolean Data

data Bool = True | False
Boolean Functions

otherwise = True

not True = False
not False = True
Boolean Operators

True && x = x
False && _ = False

(||) True _ = True
(||) False x = x
-- Parenthesis let us use operators prefix.
Operator Precedence

infixr 3 &&
infixr 2 ||

-- Ten precedence levels: 0 binds least tightly, 9
(default) binds most tightly.

-- Three associativities: infixl (default), infixr,
infix (non-associative).
Types


“Types in Haskell express high-level design in the same
way that UML diagrams do in Object Oriented
languages.”

                                — Simon Peyton-Jones
Types
ghci> :l example




“Types in Haskell express high-level design in the same
way that UML diagrams do in Object Oriented
languages.”

                                — Simon Peyton-Jones
ghci> :l example
[1 of 1] Compiling Main
( example.hs, interpreted )
Ok, modules loaded: Main.
ghci>
ghci> :l example
[1 of 1] Compiling Main
( example.hs, interpreted )
Ok, modules loaded: Main.
ghci> :r
ghci> :l example
[1 of 1] Compiling Main
( example.hs, interpreted )
Ok, modules loaded: Main.
ghci> :r
Ok, modules loaded: Main.
ghci>
ghci> :l example
[1 of 1] Compiling Main
( example.hs, interpreted )
Ok, modules loaded: Main.
ghci> :r
Ok, modules loaded: Main.
ghci> :type red
ghci> :l example
[1 of 1] Compiling Main
( example.hs, interpreted )
Ok, modules loaded: Main.
ghci> :r
Ok, modules loaded: Main.
ghci> :type red
Red :: Color
ghci>
ghci> :l example
[1 of 1] Compiling Main
( example.hs, interpreted )
Ok, modules loaded: Main.
ghci> :r
Ok, modules loaded: Main.
ghci> :type red
Red :: Color
ghci> :t isRed
Types
ghci> :l example
[1 of 1] Compiling Main
( example.hs, interpreted )
Ok, :: Color loaded: Main.
 red modules
ghci> Double
 nan :: :r
Ok, modules loaded: Main.
ghci> Color -> Double
 hue :: :type red
Red :: Color
 otherwise :: Bool
ghci> :t isRed
isRed Bool -> Bool Bool
 not :: :: Color ->
ghci> (||) :: Bool -> Bool -> Bool
 (&&),
Types

red :: Color
nan :: Double

hue :: Color -> Double

otherwise :: Bool
not :: Bool -> Bool
(&&), (||) :: Bool -> Bool -> Bool
Recursive Data

data Color = Red | Green | Blue
           | Mix Color Color
Recursive Data

data Color = Red | Green | Blue
           | Mix Color Color

mix :: Color -> Color -> Color
mix = Mix
-- Mix is a type constructor function.
Recursive Data

yellow, cyan, magenta :: Color
yellow = Mix Red Green

Mix cyan magenta =
            Mix (Mix Green Blue) (Mix Red Blue)
-- Constructor functions can be used for pattern
matching, but variables bind.
Recursive Functions

isRed   :: Color -> Bool
isRed   Red        = True
isRed   (Mix c c') = isRed c && isRed c'
isRed   _          = False
Recursive Functions

hue   :: Color -> Double
hue   Red     =0
hue   Green = 120
hue   Blue    = 240
Recursive Functions

hue   :: Color -> Double
hue   Red     =0
hue   Green = 120
hue   Blue    = 240

hue (Mix c c') = ???
hue (Mix c c') = ???
hue (Mix c c') = ???


                       h
hue (Mix c c') = let
    h = hue c
    ???
                       h
h'
hue (Mix c c') = let
    h = hue c
    ???
                            h
h'
hue (Mix c c') = let
    h = hue c
    h' = hue c'
    ???                     h
h'   m
hue (Mix c c') = let
    h = hue c
    h' = hue c'
    ???                         h
h'   m
hue (Mix c c') = let
    h = hue c
    h' = hue c'
    m = average h h'            h
   ???
h'   m
hue (Mix c c') = let
    h = hue c
    h' = hue c'
    m = average h h'                    h

   average x y = abs (x + y) / 2
   ???
h'   m
hue (Mix c c') = let
    h = hue c
    h' = hue c'
    m = average h h'                     h

    average x y = abs (x + y) / 2
  in m
h'   m
hue (Mix c c') = let
    h = hue c
    h' = hue c'
    m = average h h'                     h

    average x y = abs (x + y) / 2
  in ??!
m
hue (Mix c c') = let
    h = hue c
    h' = hue c'
    m = average h h'                 h

    average x y = abs (x + y) / 2
  in ??!

                                h'
m
hue (Mix c c') = let
    h = hue c
    h' = hue c'
    m = average h h'                      h

    average x y = abs (x + y) / 2
  in ??!

                                h'   m'
m
hue (Mix c c') = let
    h = hue c
    h' = hue c'
    m = average h h'                      h
    m' = m + 180

    average x y = abs (x + y) / 2
  in ??!
                                h'   m'
m    d
hue (Mix c c') = let
    h = hue c
    h' = hue c'
    m = average h h'                      h
    m' = m + 180

    average x y = abs (x + y) / 2
  in ??!
                                h'   m'
m    d
hue (Mix c c') = let
    h = hue c
    h' = hue c'
    m = average h h'                      h
    m' = m + 180
    d = distance h m

    average x y = abs (x + y) / 2
  in ??!                        h'   m'
m    d
hue (Mix c c') = let
    h = hue c
    h' = hue c'
    m = average h h'                     h
    m' = m + 180
    d = distance h m

    average x y = abs (x + y) / 2
    distance x y = abs (x - y) h'   m'
  in ??!
m    d
hue (Mix c c') = let
    h = hue c
    h' = hue c'
    m = average h h'                     h
    m' = m + 180
    d = distance h m

    average x y = abs (x + y) / 2
    distance x y = abs (x - y) h'   m'
  in case compare d 90 of
    LT -> m
    EQ -> ??!
    GT -> m'
m    d
hue (Mix c c') = let
    h = hue c
    h' = hue c'
    m = average h h'                     h
    m' = m + 180
    d = distance h m

    average x y = abs (x + y) / 2
    distance x y = abs (x - y) h'   m'
  in case compare d 90 of
    LT -> m
    EQ -> nan
    GT -> m'
m    d
hue (Mix c c') = r where
  r = case compare d 90 of
    LT -> m
    EQ -> nan                             h
    GT -> m'
  h = hue c
  h' = hue c'
  m = average h h'
  m' = m + 180                  h'   m'
  d = distance h m

average x y = abs (x + y) / 2
distance x y = abs (x - y)
Testing


test-framework   organize tests

HUnit            what you’re used to

QuickCheck       test properties with

                 automatically generated data
QuickCheck

prop_hue_bounds c = let h = hue c in
  isNaN h || 0 <= h && h < 360
QuickCheck

prop_hue_bounds c = let h = hue c in
  isNaN h || 0 <= h && h < 360

prop_hue_mix_reflexivity c = let h = hue c in
  isNaN h || hue (Mix c c) == h
QuickCheck

prop_hue_bounds c = let h = hue c in
  isNaN h || 0 <= h && h < 360

prop_hue_mix_reflexivity c = let h = hue c in
  isNaN h || hue (Mix c c) == h

prop_hue_mix_commutativity c c' =
  let h = hue (Mix c c') in
    isNaN h || hue (Mix c' c) == h
QuickCheck
ghci> quickCheck prop_hue_mix_commutativi
ty


prop_hue_bounds c = let h = hue c in
  isNaN h || 0 <= h && h < 360

prop_hue_mix_reflexivity c = let h = hue c in
  isNaN h || hue (Mix c c) == h

prop_hue_mix_commutativity c c' =
  let h = hue (Mix c c') in
    isNaN h || hue (Mix c' c) == h
ghci> quickCheck prop_hue_mix_commutativi
ty
+++ OK, passed 100 tests.
ghci>
ghci> quickCheck prop_hue_mix_commutativi
ty
+++ OK, passed 100 tests.
ghci> quickCheck prop_hue_mix_reflexivity
ghci> quickCheck prop_hue_mix_commutativi
ty
+++ OK, passed 100 tests.
ghci> quickCheck prop_hue_mix_reflexivity
+++ OK, passed 100 tests.
ghci>
ghci> quickCheck prop_hue_mix_commutativi
ty
+++ OK, passed 100 tests.
ghci> quickCheck prop_hue_mix_reflexivity
+++ OK, passed 100 tests.
ghci> quickCheck prop_hue_bounds
ghci> quickCheck prop_hue_mix_commutativi
ty
+++ OK, passed 100 tests.
ghci> quickCheck prop_hue_mix_reflexivity
+++ OK, passed 100 tests.
ghci> quickCheck prop_hue_bounds
*** Failed! Falsifiable (after 3 tests):
Mix (Mix Red Blue) (Mix Green Red)
ghci>
ghci> quickCheck prop_hue_mix_commutativi
ty
+++ OK, passed 100 tests.
ghci> quickCheck prop_hue_mix_reflexivity
+++ OK, passed 100 tests.
ghci> quickCheck prop_hue_bounds
*** Failed! Falsifiable (after 3 tests):
Mix (Mix Red Blue) (Mix Green Red)
ghci> hue (Mix magenta yellow)
ghci> quickCheck prop_hue_mix_commutativi
ty
+++ OK, passed 100 tests.
ghci> quickCheck prop_hue_mix_reflexivity
+++ OK, passed 100 tests.
ghci> quickCheck prop_hue_bounds
*** Failed! Falsifiable (after 3 tests):
Mix (Mix Red Blue) (Mix Green Red)
ghci> hue (Mix magenta yellow)
360.0
ghci>
h'
hue (Mix c c') = r where
  r = case compare d 90 of
    LT -> m
    EQ -> nan              m          m'
    GT -> m'
  h = hue c
  h' = hue c'
  m = average h h'
                             d   h
  m' = m + 180
  d = distance h m
h'
hue (Mix c c') = r where
  r = case compare d 90 of
    LT -> m
    EQ -> nan              m          m'
    GT -> m'
  h = hue c
  h' = hue c'
  m = average h h'
                             d   h
  m' = normalize (m + 180)
  d = distance h m
h'
hue (Mix c c') = r where
  r = case compare d 90 of
    LT -> m
    EQ -> nan              m             m'
    GT -> m'
  h = hue c
  h' = hue c'
  m = average h h'
                             d      h
  m' = normalize (m + 180)
  d = distance h m

normalize h | h < 360 = h
            | otherwise = h - 360
h'
hue (Mix c c') = r where
  r = case compare d 90 of
    LT -> m
    EQ -> nan              m                    m'
    GT -> m'
  h = hue c
  h' = hue c'
  m = average h h'
                             d            h
  m' = normalize (m + 180)
  d = distance h m

normalize h | h < 360 = h
            | otherwise = normalize (h - 360)
ghci>                                      h'
 hue (Mix c c') = r where
   r = case compare d 90 of
     LT -> m
     EQ -> nan              m                   m'
     GT -> m'
   h = hue c
   h' = hue c'
   m = average h h'
                              d           h
   m' = normalize (m + 180)
   d = distance h m

normalize h | h < 360 = h
            | otherwise = normalize (h - 360)
ghci> quickCheck prop_hue_bounds



                                   m'
ghci> quickCheck prop_hue_bounds
+++ OK, passed 100 tests.
ghci>
                                   m'
QuickCheck

prop_hue_mix_nothing c c' =
 distance (hue c) (hue c') == 180 ==>
   isNaN (hue (Mix c c'))
QuickCheck
ghci> quickCheck prop_hue_mix_nothing



prop_hue_mix_nothing c c' =
 distance (hue c) (hue c') == 180 ==>
   isNaN (hue (Mix c c'))
QuickCheck
ghci> quickCheck prop_hue_mix_nothing
*** Gave up! Passed only 23 tests.
ghci>
prop_hue_mix_nothing c c' =
 distance (hue c) (hue c') == 180 ==>
   isNaN (hue (Mix c c'))
QuickCheck

prop_hue_mix_nothing c c' =
 distance (hue c) (hue c') == 180 ==>
   isNaN (hue (Mix c c'))
QuickCheck

prop_hue_mix_nothing c c' =
 distance (hue c) (hue c') == 180 ==>
   isNaN (hue (Mix c c'))

-- Can we easily find the complement of a color?
complement   Red        =   ???
complement   Green      =   ???
complement   Blue       =   ???
complement   (Mix c c') =   ???
complement   Red        =   cyan
complement   Green      =   ???
complement   Blue       =   ???
complement   (Mix c c') =   ???
complement   Red        =   cyan
complement   Green      =   magenta
complement   Blue       =   ???
complement   (Mix c c') =   ???
complement   Red        =   cyan
complement   Green      =   magenta
complement   Blue       =   yellow
complement   (Mix c c') =   ???
complement   Red        =   cyan
complement   Green      =   magenta
complement   Blue       =   yellow
complement   (Mix c c') =   Mix ???
                                 ???
complement   Red        =   cyan
complement   Green      =   magenta
complement   Blue       =   yellow
complement   (Mix c c') =   Mix (complement c )
                                 (complement c' )
QuickCheck

prop_complement c = let h = hue c in
  not (isNaN h) ==>
    distance h (hue (complement c)) == 180
QuickCheck

prop_complement c = let h = hue c in
  not (isNaN h) ==>
    distance h (hue (complement c)) == 180

prop_hue_mix_complement c =
 isNaN (hue (Mix c (complement c)))
QuickCheck
ghci> quickCheck prop_complement



prop_complement c = let h = hue c in
  not (isNaN h) ==>
    distance h (hue (complement c)) == 180

prop_hue_mix_complement c =
 isNaN (hue (Mix c (complement c)))
ghci> quickCheck prop_complement
+++ OK, passed 100 tests.
ghci>
ghci> quickCheck prop_complement
+++ OK, passed 100 tests.
ghci> quickCheck prop_hue_mix_complement
ghci> quickCheck prop_complement
+++ OK, passed 100 tests.
ghci> quickCheck prop_hue_mix_complement
+++ OK, passed 100 tests.
ghci>
To be continued...
Summary


Haskell is functional.

Haskell has types.

QuickCheck is cool.
Preview: Infinite Lists

primes = sieve [2..] where
  sieve (p:xs) =
    p : sieve [x | x <- xs, rem x p /= 0]
Preview: IO (echo.hs)

import System.Environment (getArgs)
import Data.List (intercalate)

main = do
  args <- getArgs
  putStrLn (intercalate " " args)
Preview: Parsers
Preview: Parse JSON

data Value =   String   String
           |   Number   Double
           |   Object   [(String, Value)]
           |   Array    [Value]
           |   Bool     Bool
           |   Null
Preview: Parse JSON

value = String     <$>jsstring
    <|> Number <$>number
    <|> Object     <$>commaGroup '{' pair '}'
    <|> Array      <$>commaGroup '[' value ']'
    <|> Bool True <$ string "true"
    <|> Bool False <$ string "false"
    <|> Null       <$ string "null"
Preview: Parse JSON

pair :: Parser (String, Value)
pair = do
  s <- jsstring
  sp_char_sp ':'
  v <- value
  spaces
  return (s, v)
To be continued...

More Related Content

What's hot

Break Free with Managed Functional Programming: An Introduction to F#
Break Free with Managed Functional Programming: An Introduction to F#Break Free with Managed Functional Programming: An Introduction to F#
Break Free with Managed Functional Programming: An Introduction to F#IndyMobileNetDev
 
Break Free with Managed Functional Programming: An Introduction to F#
Break Free with Managed Functional Programming: An Introduction to F#Break Free with Managed Functional Programming: An Introduction to F#
Break Free with Managed Functional Programming: An Introduction to F#Dave Fancher
 
Introduction to Hanjp-IM Project (DebConf18 - Hsinchu, Taiwan)
Introduction to Hanjp-IM Project (DebConf18 - Hsinchu, Taiwan)Introduction to Hanjp-IM Project (DebConf18 - Hsinchu, Taiwan)
Introduction to Hanjp-IM Project (DebConf18 - Hsinchu, Taiwan)Youngbin Han
 
Ruby and Rails short motivation
Ruby and Rails short motivationRuby and Rails short motivation
Ruby and Rails short motivationjistr
 
2012-02-15 jfokus2012 - regex applied
2012-02-15 jfokus2012 - regex applied2012-02-15 jfokus2012 - regex applied
2012-02-15 jfokus2012 - regex appliedStaffan Nöteberg
 
Beam me up, scotty (PUG Roma)
Beam me up, scotty (PUG Roma)Beam me up, scotty (PUG Roma)
Beam me up, scotty (PUG Roma)Gianluca Padovani
 
NLP using JavaScript Natural Library
NLP using JavaScript Natural LibraryNLP using JavaScript Natural Library
NLP using JavaScript Natural LibraryAniruddha Chakrabarti
 
Julia language: inside the corporation
Julia language: inside the corporationJulia language: inside the corporation
Julia language: inside the corporationAndre Pemmelaar
 
Intelligent System Scripting Language - Conceptual Presentation
Intelligent System Scripting Language - Conceptual PresentationIntelligent System Scripting Language - Conceptual Presentation
Intelligent System Scripting Language - Conceptual PresentationCédric Poottaren
 
Meta Programming in Ruby - Code Camp 2010
Meta Programming in Ruby - Code Camp 2010Meta Programming in Ruby - Code Camp 2010
Meta Programming in Ruby - Code Camp 2010ssoroka
 
GraphQL in Ruby on Rails - basics
GraphQL in Ruby on Rails - basicsGraphQL in Ruby on Rails - basics
GraphQL in Ruby on Rails - basicsVisuality
 
Automating boring and repetitive UbuCon Asia video and subtitle stuffs
Automating boring and repetitive UbuCon Asia video and subtitle stuffsAutomating boring and repetitive UbuCon Asia video and subtitle stuffs
Automating boring and repetitive UbuCon Asia video and subtitle stuffsYoungbin Han
 
Functions, anonymous functions and the function type
Functions, anonymous functions and the function typeFunctions, anonymous functions and the function type
Functions, anonymous functions and the function typeChang John
 
Dart: A Replacement for JavaScript and Why You Should Care
Dart: A Replacement for JavaScript and Why You Should CareDart: A Replacement for JavaScript and Why You Should Care
Dart: A Replacement for JavaScript and Why You Should CareKevin Gisi
 
PHP Reactive Programming at Medan Tech Day 2018
PHP Reactive Programming at Medan Tech Day 2018PHP Reactive Programming at Medan Tech Day 2018
PHP Reactive Programming at Medan Tech Day 2018Dolly Aswin Harahap
 
How I Learned to Stop Worrying and Love Legacy Code.....
How I Learned to Stop Worrying and Love Legacy Code.....How I Learned to Stop Worrying and Love Legacy Code.....
How I Learned to Stop Worrying and Love Legacy Code.....Mike Harris
 
Build software like a bag of marbles, not a castle of LEGO®
Build software like a bag of marbles, not a castle of LEGO®Build software like a bag of marbles, not a castle of LEGO®
Build software like a bag of marbles, not a castle of LEGO®Hannes Lowette
 

What's hot (19)

Break Free with Managed Functional Programming: An Introduction to F#
Break Free with Managed Functional Programming: An Introduction to F#Break Free with Managed Functional Programming: An Introduction to F#
Break Free with Managed Functional Programming: An Introduction to F#
 
Break Free with Managed Functional Programming: An Introduction to F#
Break Free with Managed Functional Programming: An Introduction to F#Break Free with Managed Functional Programming: An Introduction to F#
Break Free with Managed Functional Programming: An Introduction to F#
 
Introduction to Hanjp-IM Project (DebConf18 - Hsinchu, Taiwan)
Introduction to Hanjp-IM Project (DebConf18 - Hsinchu, Taiwan)Introduction to Hanjp-IM Project (DebConf18 - Hsinchu, Taiwan)
Introduction to Hanjp-IM Project (DebConf18 - Hsinchu, Taiwan)
 
Stay fresh
Stay freshStay fresh
Stay fresh
 
Ruby and Rails short motivation
Ruby and Rails short motivationRuby and Rails short motivation
Ruby and Rails short motivation
 
2012-02-15 jfokus2012 - regex applied
2012-02-15 jfokus2012 - regex applied2012-02-15 jfokus2012 - regex applied
2012-02-15 jfokus2012 - regex applied
 
Beam me up, scotty (PUG Roma)
Beam me up, scotty (PUG Roma)Beam me up, scotty (PUG Roma)
Beam me up, scotty (PUG Roma)
 
NLP using JavaScript Natural Library
NLP using JavaScript Natural LibraryNLP using JavaScript Natural Library
NLP using JavaScript Natural Library
 
Julia language: inside the corporation
Julia language: inside the corporationJulia language: inside the corporation
Julia language: inside the corporation
 
Why Scala?
Why Scala?Why Scala?
Why Scala?
 
Intelligent System Scripting Language - Conceptual Presentation
Intelligent System Scripting Language - Conceptual PresentationIntelligent System Scripting Language - Conceptual Presentation
Intelligent System Scripting Language - Conceptual Presentation
 
Meta Programming in Ruby - Code Camp 2010
Meta Programming in Ruby - Code Camp 2010Meta Programming in Ruby - Code Camp 2010
Meta Programming in Ruby - Code Camp 2010
 
GraphQL in Ruby on Rails - basics
GraphQL in Ruby on Rails - basicsGraphQL in Ruby on Rails - basics
GraphQL in Ruby on Rails - basics
 
Automating boring and repetitive UbuCon Asia video and subtitle stuffs
Automating boring and repetitive UbuCon Asia video and subtitle stuffsAutomating boring and repetitive UbuCon Asia video and subtitle stuffs
Automating boring and repetitive UbuCon Asia video and subtitle stuffs
 
Functions, anonymous functions and the function type
Functions, anonymous functions and the function typeFunctions, anonymous functions and the function type
Functions, anonymous functions and the function type
 
Dart: A Replacement for JavaScript and Why You Should Care
Dart: A Replacement for JavaScript and Why You Should CareDart: A Replacement for JavaScript and Why You Should Care
Dart: A Replacement for JavaScript and Why You Should Care
 
PHP Reactive Programming at Medan Tech Day 2018
PHP Reactive Programming at Medan Tech Day 2018PHP Reactive Programming at Medan Tech Day 2018
PHP Reactive Programming at Medan Tech Day 2018
 
How I Learned to Stop Worrying and Love Legacy Code.....
How I Learned to Stop Worrying and Love Legacy Code.....How I Learned to Stop Worrying and Love Legacy Code.....
How I Learned to Stop Worrying and Love Legacy Code.....
 
Build software like a bag of marbles, not a castle of LEGO®
Build software like a bag of marbles, not a castle of LEGO®Build software like a bag of marbles, not a castle of LEGO®
Build software like a bag of marbles, not a castle of LEGO®
 

Similar to Haskell: A Functional Language for Aesthetics, Pragmatics and Performance

Functional programming with Xtend
Functional programming with XtendFunctional programming with Xtend
Functional programming with XtendSven Efftinge
 
Programming Paradigms
Programming ParadigmsProgramming Paradigms
Programming ParadigmsJaneve George
 
Os Keysholistic
Os KeysholisticOs Keysholistic
Os Keysholisticoscon2007
 
Elasticsearch Basics
Elasticsearch BasicsElasticsearch Basics
Elasticsearch BasicsShifa Khan
 
Scala: functional programming for the imperative mind
Scala: functional programming for the imperative mindScala: functional programming for the imperative mind
Scala: functional programming for the imperative mindSander Mak (@Sander_Mak)
 
Programming Paradigms
Programming ParadigmsProgramming Paradigms
Programming ParadigmsDirecti Group
 
Introduction to Scala
Introduction to ScalaIntroduction to Scala
Introduction to ScalaJohan Andrén
 
sete linguagens em sete semanas
sete linguagens em sete semanassete linguagens em sete semanas
sete linguagens em sete semanastdc-globalcode
 
Александр Ломов: "Reactjs + Haskell + Cloud Foundry = Love"
Александр Ломов: "Reactjs + Haskell + Cloud Foundry = Love"Александр Ломов: "Reactjs + Haskell + Cloud Foundry = Love"
Александр Ломов: "Reactjs + Haskell + Cloud Foundry = Love"Olga Lavrentieva
 
[WebCamp2014] Towards functional web
[WebCamp2014] Towards functional web[WebCamp2014] Towards functional web
[WebCamp2014] Towards functional webBlaž Repas
 
PL Lecture 01 - preliminaries
PL Lecture 01 - preliminariesPL Lecture 01 - preliminaries
PL Lecture 01 - preliminariesSchwannden Kuo
 
The Holistic Programmer
The Holistic ProgrammerThe Holistic Programmer
The Holistic ProgrammerAdam Keys
 
BayFP: Concurrent and Multicore Haskell
BayFP: Concurrent and Multicore HaskellBayFP: Concurrent and Multicore Haskell
BayFP: Concurrent and Multicore HaskellBryan O'Sullivan
 
Little words of wisdom for the developer - Guillaume Laforge (Pivotal)
Little words of wisdom for the developer - Guillaume Laforge (Pivotal)Little words of wisdom for the developer - Guillaume Laforge (Pivotal)
Little words of wisdom for the developer - Guillaume Laforge (Pivotal)jaxLondonConference
 

Similar to Haskell: A Functional Language for Aesthetics, Pragmatics and Performance (20)

Functional programming with Xtend
Functional programming with XtendFunctional programming with Xtend
Functional programming with Xtend
 
TypeScript
TypeScriptTypeScript
TypeScript
 
Programming Paradigms
Programming ParadigmsProgramming Paradigms
Programming Paradigms
 
Os Keysholistic
Os KeysholisticOs Keysholistic
Os Keysholistic
 
Elasticsearch Basics
Elasticsearch BasicsElasticsearch Basics
Elasticsearch Basics
 
Presentation
PresentationPresentation
Presentation
 
Scala: functional programming for the imperative mind
Scala: functional programming for the imperative mindScala: functional programming for the imperative mind
Scala: functional programming for the imperative mind
 
Programming Paradigms
Programming ParadigmsProgramming Paradigms
Programming Paradigms
 
Swift vs. Language X
Swift vs. Language XSwift vs. Language X
Swift vs. Language X
 
Introduction to Scala
Introduction to ScalaIntroduction to Scala
Introduction to Scala
 
sete linguagens em sete semanas
sete linguagens em sete semanassete linguagens em sete semanas
sete linguagens em sete semanas
 
Александр Ломов: "Reactjs + Haskell + Cloud Foundry = Love"
Александр Ломов: "Reactjs + Haskell + Cloud Foundry = Love"Александр Ломов: "Reactjs + Haskell + Cloud Foundry = Love"
Александр Ломов: "Reactjs + Haskell + Cloud Foundry = Love"
 
Jax keynote
Jax keynoteJax keynote
Jax keynote
 
[WebCamp2014] Towards functional web
[WebCamp2014] Towards functional web[WebCamp2014] Towards functional web
[WebCamp2014] Towards functional web
 
PL Lecture 01 - preliminaries
PL Lecture 01 - preliminariesPL Lecture 01 - preliminaries
PL Lecture 01 - preliminaries
 
The Holistic Programmer
The Holistic ProgrammerThe Holistic Programmer
The Holistic Programmer
 
BayFP: Concurrent and Multicore Haskell
BayFP: Concurrent and Multicore HaskellBayFP: Concurrent and Multicore Haskell
BayFP: Concurrent and Multicore Haskell
 
Introduction to Scala
Introduction to ScalaIntroduction to Scala
Introduction to Scala
 
Scala: An OO Surprise
Scala: An OO SurpriseScala: An OO Surprise
Scala: An OO Surprise
 
Little words of wisdom for the developer - Guillaume Laforge (Pivotal)
Little words of wisdom for the developer - Guillaume Laforge (Pivotal)Little words of wisdom for the developer - Guillaume Laforge (Pivotal)
Little words of wisdom for the developer - Guillaume Laforge (Pivotal)
 

Recently uploaded

A Deep Dive on Passkeys: FIDO Paris Seminar.pptx
A Deep Dive on Passkeys: FIDO Paris Seminar.pptxA Deep Dive on Passkeys: FIDO Paris Seminar.pptx
A Deep Dive on Passkeys: FIDO Paris Seminar.pptxLoriGlavin3
 
Ensuring Technical Readiness For Copilot in Microsoft 365
Ensuring Technical Readiness For Copilot in Microsoft 365Ensuring Technical Readiness For Copilot in Microsoft 365
Ensuring Technical Readiness For Copilot in Microsoft 3652toLead Limited
 
How AI, OpenAI, and ChatGPT impact business and software.
How AI, OpenAI, and ChatGPT impact business and software.How AI, OpenAI, and ChatGPT impact business and software.
How AI, OpenAI, and ChatGPT impact business and software.Curtis Poe
 
Merck Moving Beyond Passwords: FIDO Paris Seminar.pptx
Merck Moving Beyond Passwords: FIDO Paris Seminar.pptxMerck Moving Beyond Passwords: FIDO Paris Seminar.pptx
Merck Moving Beyond Passwords: FIDO Paris Seminar.pptxLoriGlavin3
 
The Ultimate Guide to Choosing WordPress Pros and Cons
The Ultimate Guide to Choosing WordPress Pros and ConsThe Ultimate Guide to Choosing WordPress Pros and Cons
The Ultimate Guide to Choosing WordPress Pros and ConsPixlogix Infotech
 
DevEX - reference for building teams, processes, and platforms
DevEX - reference for building teams, processes, and platformsDevEX - reference for building teams, processes, and platforms
DevEX - reference for building teams, processes, and platformsSergiu Bodiu
 
Commit 2024 - Secret Management made easy
Commit 2024 - Secret Management made easyCommit 2024 - Secret Management made easy
Commit 2024 - Secret Management made easyAlfredo García Lavilla
 
Dev Dives: Streamline document processing with UiPath Studio Web
Dev Dives: Streamline document processing with UiPath Studio WebDev Dives: Streamline document processing with UiPath Studio Web
Dev Dives: Streamline document processing with UiPath Studio WebUiPathCommunity
 
The Role of FIDO in a Cyber Secure Netherlands: FIDO Paris Seminar.pptx
The Role of FIDO in a Cyber Secure Netherlands: FIDO Paris Seminar.pptxThe Role of FIDO in a Cyber Secure Netherlands: FIDO Paris Seminar.pptx
The Role of FIDO in a Cyber Secure Netherlands: FIDO Paris Seminar.pptxLoriGlavin3
 
Take control of your SAP testing with UiPath Test Suite
Take control of your SAP testing with UiPath Test SuiteTake control of your SAP testing with UiPath Test Suite
Take control of your SAP testing with UiPath Test SuiteDianaGray10
 
Hyperautomation and AI/ML: A Strategy for Digital Transformation Success.pdf
Hyperautomation and AI/ML: A Strategy for Digital Transformation Success.pdfHyperautomation and AI/ML: A Strategy for Digital Transformation Success.pdf
Hyperautomation and AI/ML: A Strategy for Digital Transformation Success.pdfPrecisely
 
Unleash Your Potential - Namagunga Girls Coding Club
Unleash Your Potential - Namagunga Girls Coding ClubUnleash Your Potential - Namagunga Girls Coding Club
Unleash Your Potential - Namagunga Girls Coding ClubKalema Edgar
 
The State of Passkeys with FIDO Alliance.pptx
The State of Passkeys with FIDO Alliance.pptxThe State of Passkeys with FIDO Alliance.pptx
The State of Passkeys with FIDO Alliance.pptxLoriGlavin3
 
Connect Wave/ connectwave Pitch Deck Presentation
Connect Wave/ connectwave Pitch Deck PresentationConnect Wave/ connectwave Pitch Deck Presentation
Connect Wave/ connectwave Pitch Deck PresentationSlibray Presentation
 
TeamStation AI System Report LATAM IT Salaries 2024
TeamStation AI System Report LATAM IT Salaries 2024TeamStation AI System Report LATAM IT Salaries 2024
TeamStation AI System Report LATAM IT Salaries 2024Lonnie McRorey
 
Transcript: New from BookNet Canada for 2024: Loan Stars - Tech Forum 2024
Transcript: New from BookNet Canada for 2024: Loan Stars - Tech Forum 2024Transcript: New from BookNet Canada for 2024: Loan Stars - Tech Forum 2024
Transcript: New from BookNet Canada for 2024: Loan Stars - Tech Forum 2024BookNet Canada
 
How to write a Business Continuity Plan
How to write a Business Continuity PlanHow to write a Business Continuity Plan
How to write a Business Continuity PlanDatabarracks
 
Gen AI in Business - Global Trends Report 2024.pdf
Gen AI in Business - Global Trends Report 2024.pdfGen AI in Business - Global Trends Report 2024.pdf
Gen AI in Business - Global Trends Report 2024.pdfAddepto
 
WordPress Websites for Engineers: Elevate Your Brand
WordPress Websites for Engineers: Elevate Your BrandWordPress Websites for Engineers: Elevate Your Brand
WordPress Websites for Engineers: Elevate Your Brandgvaughan
 

Recently uploaded (20)

A Deep Dive on Passkeys: FIDO Paris Seminar.pptx
A Deep Dive on Passkeys: FIDO Paris Seminar.pptxA Deep Dive on Passkeys: FIDO Paris Seminar.pptx
A Deep Dive on Passkeys: FIDO Paris Seminar.pptx
 
Ensuring Technical Readiness For Copilot in Microsoft 365
Ensuring Technical Readiness For Copilot in Microsoft 365Ensuring Technical Readiness For Copilot in Microsoft 365
Ensuring Technical Readiness For Copilot in Microsoft 365
 
How AI, OpenAI, and ChatGPT impact business and software.
How AI, OpenAI, and ChatGPT impact business and software.How AI, OpenAI, and ChatGPT impact business and software.
How AI, OpenAI, and ChatGPT impact business and software.
 
Merck Moving Beyond Passwords: FIDO Paris Seminar.pptx
Merck Moving Beyond Passwords: FIDO Paris Seminar.pptxMerck Moving Beyond Passwords: FIDO Paris Seminar.pptx
Merck Moving Beyond Passwords: FIDO Paris Seminar.pptx
 
The Ultimate Guide to Choosing WordPress Pros and Cons
The Ultimate Guide to Choosing WordPress Pros and ConsThe Ultimate Guide to Choosing WordPress Pros and Cons
The Ultimate Guide to Choosing WordPress Pros and Cons
 
DevEX - reference for building teams, processes, and platforms
DevEX - reference for building teams, processes, and platformsDevEX - reference for building teams, processes, and platforms
DevEX - reference for building teams, processes, and platforms
 
Commit 2024 - Secret Management made easy
Commit 2024 - Secret Management made easyCommit 2024 - Secret Management made easy
Commit 2024 - Secret Management made easy
 
Dev Dives: Streamline document processing with UiPath Studio Web
Dev Dives: Streamline document processing with UiPath Studio WebDev Dives: Streamline document processing with UiPath Studio Web
Dev Dives: Streamline document processing with UiPath Studio Web
 
The Role of FIDO in a Cyber Secure Netherlands: FIDO Paris Seminar.pptx
The Role of FIDO in a Cyber Secure Netherlands: FIDO Paris Seminar.pptxThe Role of FIDO in a Cyber Secure Netherlands: FIDO Paris Seminar.pptx
The Role of FIDO in a Cyber Secure Netherlands: FIDO Paris Seminar.pptx
 
Take control of your SAP testing with UiPath Test Suite
Take control of your SAP testing with UiPath Test SuiteTake control of your SAP testing with UiPath Test Suite
Take control of your SAP testing with UiPath Test Suite
 
Hyperautomation and AI/ML: A Strategy for Digital Transformation Success.pdf
Hyperautomation and AI/ML: A Strategy for Digital Transformation Success.pdfHyperautomation and AI/ML: A Strategy for Digital Transformation Success.pdf
Hyperautomation and AI/ML: A Strategy for Digital Transformation Success.pdf
 
Unleash Your Potential - Namagunga Girls Coding Club
Unleash Your Potential - Namagunga Girls Coding ClubUnleash Your Potential - Namagunga Girls Coding Club
Unleash Your Potential - Namagunga Girls Coding Club
 
DMCC Future of Trade Web3 - Special Edition
DMCC Future of Trade Web3 - Special EditionDMCC Future of Trade Web3 - Special Edition
DMCC Future of Trade Web3 - Special Edition
 
The State of Passkeys with FIDO Alliance.pptx
The State of Passkeys with FIDO Alliance.pptxThe State of Passkeys with FIDO Alliance.pptx
The State of Passkeys with FIDO Alliance.pptx
 
Connect Wave/ connectwave Pitch Deck Presentation
Connect Wave/ connectwave Pitch Deck PresentationConnect Wave/ connectwave Pitch Deck Presentation
Connect Wave/ connectwave Pitch Deck Presentation
 
TeamStation AI System Report LATAM IT Salaries 2024
TeamStation AI System Report LATAM IT Salaries 2024TeamStation AI System Report LATAM IT Salaries 2024
TeamStation AI System Report LATAM IT Salaries 2024
 
Transcript: New from BookNet Canada for 2024: Loan Stars - Tech Forum 2024
Transcript: New from BookNet Canada for 2024: Loan Stars - Tech Forum 2024Transcript: New from BookNet Canada for 2024: Loan Stars - Tech Forum 2024
Transcript: New from BookNet Canada for 2024: Loan Stars - Tech Forum 2024
 
How to write a Business Continuity Plan
How to write a Business Continuity PlanHow to write a Business Continuity Plan
How to write a Business Continuity Plan
 
Gen AI in Business - Global Trends Report 2024.pdf
Gen AI in Business - Global Trends Report 2024.pdfGen AI in Business - Global Trends Report 2024.pdf
Gen AI in Business - Global Trends Report 2024.pdf
 
WordPress Websites for Engineers: Elevate Your Brand
WordPress Websites for Engineers: Elevate Your BrandWordPress Websites for Engineers: Elevate Your Brand
WordPress Websites for Engineers: Elevate Your Brand
 

Haskell: A Functional Language for Aesthetics, Pragmatics and Performance