Skip to content

Instantly share code, notes, and snippets.

@ssledz
Last active June 3, 2021 19:26
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save ssledz/793967ff931b0101cdd81ce6a48f67d4 to your computer and use it in GitHub Desktop.
Save ssledz/793967ff931b0101cdd81ce6a48f67d4 to your computer and use it in GitHub Desktop.

cabal

Installing library

cabal update && cabal new-install --lib codeworld-api

lists

ghci> 1 : 2 : 3 : []
[1,2,3]
ghci> [1, 2, 3]
[1,2,3]

++ - concat two lists together

ghci> [1,2,3,4] ++ [9,10,11,12]  
[1,2,3,4,9,10,11,12]  
ghci> "hello" ++ " " ++ "world"  
"hello world"  
ghci> ['w','o'] ++ ['o','t']  
"woot"

!! - get element by index (the indices start at 0)

ghci> "Steve Buscemi" !! 6  
'B'  
ghci> [9.4,33.2,96.2,11.2,23.25] !! 1  
33.2  
ghci> head [5,4,3,2,1]  
5  
ghci> tail [5,4,3,2,1]  
[4,3,2,1]  
ghci> last [5,4,3,2,1]  
1  
ghci> init [5,4,3,2,1]  
[5,4,3,2] 
ghci> length [5,4,3,2,1]  
5 
ghci> null [1,2,3]  
False  
ghci> null []  
True 
ghci> reverse [5,4,3,2,1]  
[1,2,3,4,5] 
ghci> take 3 [5,4,3,2,1]  
[5,4,3]  
ghci> take 1 [3,9,3]  
[3]  
ghci> take 5 [1,2]  
[1,2]  
ghci> take 0 [6,6,6]  
[]
ghci> drop 3 [8,4,2,1,5,6]  
[1,5,6]  
ghci> drop 0 [1,2,3,4]  
[1,2,3,4]  
ghci> drop 100 [1,2,3,4]  
[]
ghci> minimum [8,4,2,1,5,6]  
1  
ghci> maximum [1,9,2,3,4]  
9  
ghci> sum [5,2,1,6,3,2,5,7]  
31  
ghci> product [6,2,1,2]  
24  
ghci> product [1,2,5,6,7,9,2,0]  
0   
ghci> 4 `elem` [3,4,5,6]  
True  
ghci> 10 `elem` [3,4,5,6]  
False  
ghci> take 10 (cycle [1,2,3])  
[1,2,3,1,2,3,1,2,3,1]  
ghci> take 12 (cycle "LOL ")  
"LOL LOL LOL " 
ghci> take 10 (repeat 5)  
[5,5,5,5,5,5,5,5,5,5]
ghci> zip [1,2,3,4,5] [5,5,5,5,5]  
[(1,5),(2,5),(3,5),(4,5),(5,5)]  
ghci> zip [1 .. 5] ["one", "two", "three", "four", "five"]  
[(1,"one"),(2,"two"),(3,"three"),(4,"four"),(5,"five")] 

ranges

ghci> [1..20]  
[1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20]  
ghci> ['a'..'z']  
"abcdefghijklmnopqrstuvwxyz"  
ghci> ['K'..'Z']  
"KLMNOPQRSTUVWXYZ"
ghci> [2,4..20]  
[2,4,6,8,10,12,14,16,18,20]  
ghci> [3,6..20]  
[3,6,9,12,15,18]
ghci> take 5 [1..]
[1,2,3,4,5]

list comprehension

ghci> [x*2 | x <- [1..10]]  
[2,4,6,8,10,12,14,16,18,20] 
ghci> [x*2 | x <- [1..10], x*2 >= 12]  
[12,14,16,18,20] 
ghci> [ x*y | x <- [2,5,10], y <- [8,10,11], x*y > 50]  
[55,80,100,110] 
ghci> let xxs = [[1,3,5,2,3,1,2,4,5],[1,2,3,4,5,6,7,8,9],[1,2,4,2,1,6,3,1,3,2,3,6]]  
ghci> [ [ x | x <- xs, even x ] | xs <- xxs]  
[[2,2,4],[2,4,6,8],[2,4,2,6,2,6]]  

tuples

ghci> (1, "One")
(1,"One")
ghci> (2, "Two")
(2,"Two")
ghci> fst (8,11)  
8  
ghci> fst ("Wow", False)  
"Wow" 
ghci> snd (8,11)  
11  
ghci> snd ("Wow", False)  
False

pattern matching

sayMe :: (Integral a) => a -> String  
sayMe 1 = "One!"  
sayMe 2 = "Two!"  
sayMe 3 = "Three!"  
sayMe 4 = "Four!"  
sayMe 5 = "Five!"  
sayMe x = "Not between 1 and 5"  
factorial :: (Integral a) => a -> a  
factorial 0 = 1  
factorial n = n * factorial (n - 1)  
first :: (a, b, c) -> a  
first (x, _, _) = x  
  
second :: (a, b, c) -> b  
second (_, y, _) = y  
  
third :: (a, b, c) -> c  
third (_, _, z) = z 
tell :: (Show a) => [a] -> String  
tell [] = "The list is empty"  
tell (x:[]) = "The list has one element: " ++ show x  
tell (x:y:[]) = "The list has two elements: " ++ show x ++ " and " ++ show y  
tell (x:y:_) = "This list is long. The first two elements are: " ++ show x ++ " and " ++ show y  
capital :: String -> String  
capital "" = "Empty string, whoops!"  
capital all@(x:xs) = "The first letter of " ++ all ++ " is " ++ [x] 

guards

bmiTell :: (RealFloat a) => a -> String  
bmiTell bmi  
    | bmi <= 18.5 = "You're underweight, you emo, you!"  
    | bmi <= 25.0 = "You're supposedly normal. Pffft, I bet you're ugly!"  
    | bmi <= 30.0 = "You're fat! Lose some weight, fatty!"  
    | otherwise   = "You're a whale, congratulations!" 

where

bmiTell :: (RealFloat a) => a -> a -> String  
bmiTell weight height  
    | bmi <= skinny = "You're underweight, you emo, you!"  
    | bmi <= normal = "You're supposedly normal. Pffft, I bet you're ugly!"  
    | bmi <= fat    = "You're fat! Lose some weight, fatty!"  
    | otherwise     = "You're a whale, congratulations!"  
    where bmi = weight / height ^ 2  
          skinny = 18.5  
          normal = 25.0  
          fat = 30.0
initials :: String -> String -> String  
initials firstname lastname = [f] ++ ". " ++ [l] ++ "."  
    where (f:_) = firstname  
          (l:_) = lastname 

let <bindings> in <expression>

cylinder :: (RealFloat a) => a -> a -> a  
cylinder r h = 
    let sideArea = 2 * pi * r * h  
        topArea = pi * r ^2  
    in  sideArea + 2 * topArea

case expression

case expression of pattern -> result  
                   pattern -> result  
                   pattern -> result  
                   ... 
head' :: [a] -> a  
head' xs = case xs of [] -> error "No head for empty lists!"  
                      (x:_) -> x  
describeList :: [a] -> String  
describeList xs = "The list is " ++ case xs of [] -> "empty."  
                                               [x] -> "a singleton list."   
                                               xs -> "a longer list."  

anonymous functions

ghci> (\x -> x) "Logical."
ghci> (\x -> x ++ " captain.") "Logical,"

ghci> map (\x -> x * x) [1, 2, 3]
ghci> foldl (\x carryOver -> carryOver + x) 0 [1 .. 10]
ghci> filter (\x -> rem x 2 == 0) [1, 2, 3, 4, 5]
ghci> foldl1 (+) [1 .. 3]
ghci> foldl (+) 0 [1 .. 3]

partially applied functions

ghci> let prod x y = x * y
ghci> let double = prod 2
ghci> let triple = prod 3
ghci> double 3
ghci> triple 4

lazy evaluation

ghci> let myRange start step = start : (myRange (start + step) step)
ghci> take 10 (myRange 1 2)
[1,3,5,7,9,11,13,15,17,19]

ghci> let lazyFib x y = x:(lazyFib y (x + y))
ghci> let fib = lazyFib 1 1
ghci> let fibNth x = head (drop (x - 1) (take (x) fib))

ghci> take 10 fib
[1,1,2,3,5,8,13,21,34,55]
ghci> fibNth 10
55

user defined types

ghci> data Boolean = True | False deriving Show
ghci> True
True

ghci> data Either a b = Left a | Right b deriving Show
ghci> Left 1
Left 1

ghci> data Person = Person { firstName :: String, lastName :: String } deriving (Show, Read)
ghci> let person = Person "Tom" "Tam"
ghci> person
Person {firstName = "Tom", lastName = "Tam"} 
ghci> firstName person
"Tom"
ghci> let (Person { firstName = x, lastName = y }) = read "Person {firstName = \"Tom\", lastName = \"Tam\"}"

recursive types

ghci> data Tree a = Branch [Tree a] | Leaf a deriving Show
ghci> Branch [Leaf 1, Branch [Leaf 2, Leaf 3]]

ghci> let { tmap f (Leaf a) = Leaf (f a); tmap f (Branch xs) =  Branch ( map (\x -> tmap f x) xs ) }
ghci> tmap (\x -> x + 1) (Branch [Leaf 1, Branch [], Branch [Leaf 2]])
Branch [Leaf 2,Branch [],Branch [Leaf 3]]

ghci> let { depth (Leaf _) = 1; depth (Branch []) = 1; depth (Branch xs) = 1 + maximum (map depth xs) }
ghci> depth (Branch [Leaf 1, Branch [], Branch [Leaf 2]])
3

type classes

A typeclass is a sort of interface that defines some behavior.

Show

class Show a where     
  showsPrec :: Int -> a -> ShowS
  show :: a -> String
  showList :: [a] -> ShowS
  {-# MINIMAL showsPrec | show #-}

Eq

class Eq a where
  (==) :: a -> a -> Bool
  (/=) :: a -> a -> Bool
  {-# MINIMAL (==) | (/=) #-}
ghci> 5 == 5  
True  
ghci> 5 /= 5  
False  
ghci> 'a' == 'a'  
True  
ghci> "Ho Ho" == "Ho Ho"  
True  
ghci> 3.432 == 3.432  
True 

Ord

class Eq a => Ord a where
  compare :: a -> a -> Ordering
  (<) :: a -> a -> Bool
  (<=) :: a -> a -> Bool
  (>) :: a -> a -> Bool
  (>=) :: a -> a -> Bool
  max :: a -> a -> a
  min :: a -> a -> a
  {-# MINIMAL compare | (<=) #-}
data Ordering = LT | EQ | GT
ghci> "Abrakadabra" < "Zebra"  
True  
ghci> "Abrakadabra" `compare` "Zebra"  
LT  
ghci> 5 >= 2  
True  
ghci> 5 `compare` 3  
GT  

type class instances

data TrafficLight = Red | Yellow | Green
instance Eq TrafficLight where  
    Red == Red = True  
    Green == Green = True  
    Yellow == Yellow = True  
    _ == _ = False 
instance Show TrafficLight where  
    show Red = "Red light"  
    show Yellow = "Yellow light"  
    show Green = "Green light" 
ghci> Red == Red  
True  
ghci> Red == Yellow  
False  
ghci> Red `elem` [Red, Yellow, Green]  
True  
ghci> [Red, Yellow, Green]  
[Red light,Yellow light,Green light]
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment