mirror of
https://github.com/LeCoupa/awesome-cheatsheets.git
synced 2026-01-25 04:38:51 -08:00
Created a cheatsheet for the Haskell language.
This commit is contained in:
committed by
GitHub
parent
52d590f1c3
commit
8840648ff4
479
languages/haskell.txt
Normal file
479
languages/haskell.txt
Normal file
@@ -0,0 +1,479 @@
|
||||
CHEATSHEET HASKELL
|
||||
|
||||
Use HASKELL
|
||||
|
||||
Documentation
|
||||
- Haskell API search: http://www.haskell.org/hoogle/
|
||||
- Haskell reference: ftp://ftpdeveloppez.com/cmaneu/langages/haskell/haskellreference.zip
|
||||
|
||||
Basics
|
||||
- Load file :load filename
|
||||
- Reload file :reload
|
||||
- Launch file editor with current file :edit
|
||||
- Get information about a function :info command
|
||||
|
||||
Comments
|
||||
|
||||
A single line comment starts with ‘--’ and extends to the end of the line.
|
||||
Multi-line comments start with ’{-’ and extend to ’-}’. Comments can be nested.
|
||||
|
||||
Reserved words
|
||||
|
||||
!
|
||||
'
|
||||
''
|
||||
-
|
||||
--
|
||||
-<
|
||||
-<<
|
||||
->
|
||||
::
|
||||
;
|
||||
<-
|
||||
,
|
||||
=
|
||||
=>
|
||||
>
|
||||
?
|
||||
#
|
||||
*
|
||||
@
|
||||
[|, |]
|
||||
\
|
||||
_
|
||||
`
|
||||
{, }
|
||||
{-, -}
|
||||
|
|
||||
~
|
||||
as
|
||||
case, of
|
||||
class
|
||||
data
|
||||
data family
|
||||
data instance
|
||||
default
|
||||
deriving
|
||||
deriving instance
|
||||
do
|
||||
forall
|
||||
foreign
|
||||
hiding
|
||||
if, then, else
|
||||
import
|
||||
infix, infixl, infixr
|
||||
instance
|
||||
let, in
|
||||
mdo
|
||||
module
|
||||
newtype
|
||||
proc
|
||||
qualified
|
||||
rec
|
||||
type
|
||||
type family
|
||||
type instance
|
||||
where
|
||||
|
||||
Data types
|
||||
|
||||
All the data types must start by a capital letter.
|
||||
|
||||
Int: Integer number with fixed precision
|
||||
Integer: Integer number with virtually no limits
|
||||
Float: Real floating point with single precision
|
||||
Double: Real floating point with double the precision
|
||||
Bool: Boolean
|
||||
Char: Character, have to placed between quotes
|
||||
String: A list of Chars
|
||||
|
||||
Type redefinition
|
||||
Type NewTypeName = TypeValue
|
||||
Example: Type String = [Char]
|
||||
|
||||
List & Numbers
|
||||
|
||||
[] – Empty list
|
||||
[1,2,3,4] – List of four numbers
|
||||
1 : 2 : 3 : 4 : [] - Write a lists using cons (:) and nil ([])
|
||||
[1..100] - List of number 1,2,3..,100
|
||||
[100..] - Infinite list of number 100,101,102,103,..
|
||||
[0,-1 ..] - Negative integers 0,-1,-2,..
|
||||
(h:q) - h stands for the first element of the list and q for the result
|
||||
(f:s:t:q) - f is the first element, s is the second elemnt, t is the third and q is the rest of the elements of the list.
|
||||
|
||||
It can be added the element e to the list l with e:l
|
||||
|
||||
Basic functions for lists
|
||||
|
||||
list1++list2 append two list
|
||||
list!!n return element n
|
||||
head takes a list and returns its head. The head of a list is basically its first element.
|
||||
tail takes a list and returns its tail. In other words, it chops off a list's head.
|
||||
last takes a list and returns its last element.
|
||||
init takes a list and returns everything except its last element.
|
||||
length takes a list and returns its length, obviously.
|
||||
null checks if a list is empty.
|
||||
reverse reverses a list.
|
||||
take takes number and a list. It extracts that many elements from the beginning of the list.
|
||||
drop works in a similar way as take, only it drops the number of elements from the beginning of a list.
|
||||
maximum takes a list of stuff that can be put in some kind of order and returns the biggest element.
|
||||
minimum returns the smallest.
|
||||
sum takes a list of numbers and returns their sum.
|
||||
product takes a list of numbers and returns their product.
|
||||
elem takes a thing and a list of things and tells us if that thing is an element of the list. It's usually called as an infix function because it's easier to read that way.
|
||||
|
||||
Function for infinite lists:
|
||||
|
||||
cycle: takes a list and cycles it into an infinite list. If you just try to display the result, it will go on forever so you have to slice it off somewhere.
|
||||
repeat: takes an element and produces an infinite list of just that element. It's like cycling a list with only one element.
|
||||
replicate: takes the number of the same element in a list.
|
||||
|
||||
List comprehension
|
||||
|
||||
List comprehension is the process of generating a list using a mathematical expression.
|
||||
|
||||
[body | generator]
|
||||
|
||||
Examples: [x*a | a <- [1..3]] = [2,4,6]
|
||||
[x*y | x <- [1..5], y <- [9..5] ]
|
||||
[x | x <- [1,10,14,16,18], x>5 ]
|
||||
|
||||
Tuples
|
||||
|
||||
(1,"a") - 2-element tuple of a number and a string
|
||||
(last, 4, 'b') - 3-element tuple of a function, a number and a character
|
||||
|
||||
Note that the empty tuple () is also a type which can only have a single value: ()
|
||||
|
||||
Basic functions for Tuples
|
||||
|
||||
fst: takes a pair and returns its first component.
|
||||
snd: takes a pair and returns its second component.
|
||||
zip: takes two lists and then zips them together into one list by joining the matching elements into pairs.
|
||||
|
||||
Note: these functions operate only on pairs. They won't work on triples, 4-tuples, 5-tuples, etc.
|
||||
|
||||
|
||||
Typeclasses
|
||||
|
||||
A typeclass is a sort of interface that defines some behaviour.
|
||||
If a type is a part of a typeclass, that means that it supports and implements the behavior the typeclass describes.
|
||||
If you come from OPP you can think of them kind of as Java interfaces, only better.
|
||||
|
||||
Everything before the => symbol is called a class constraint.
|
||||
|
||||
Eq is used for types that support equality testing. Eq class constraint for a type variable in a function, it uses == or /= somewhere inside its definition
|
||||
Ord is for types that have an ordering. Ord covers all the standard comparing functions such as >, <, >= and <=
|
||||
Show can be presented as strings. show takes a value whose type is a member of Show and presents it to us as a string.
|
||||
Read is sort of the opposite typeclass of Show. The read function takes a string and returns a type which is a member of Read.
|
||||
Enum members are sequentially ordered types, they can be enumerated. Types in this class: (), Bool, Char, Ordering, Int, Integer, Float and Double.
|
||||
Bounded members have an upper and a lower bound. All tuples are part of Bounded. Types in this class: Bool, Int and Char.
|
||||
Num is a numeric typeclass. Types in this class: Int, Integer, Float and Double.
|
||||
Integral is also a numeric typeclass. In this typeclass are Int and Integer.
|
||||
Floating includes only floating point numbers. Types in this class: Float and Double.
|
||||
|
||||
Functions
|
||||
|
||||
Functions are defined by declaring their name, any arguments, and an equals sign.
|
||||
|
||||
Declare a new function starting with explicit type declaration (optional)
|
||||
functionName :: inpuntType1 [ -> inputTypeN ] -> outputType
|
||||
|
||||
Declare a new function with pattern matching
|
||||
intToChar 1 = "One"
|
||||
intToChar 2 = "Two"
|
||||
|
||||
Declare a new function with guards
|
||||
intToChar x
|
||||
| x==1 = "One"
|
||||
| x==2 = "Two"
|
||||
|
||||
Declare a new function with guards and pattern matching
|
||||
allEmpty _ = falsePart
|
||||
allEmpty [] = truePart
|
||||
|
||||
alwaysEven n
|
||||
| otherwise = False
|
||||
| n 'div' 2 == 0 = True
|
||||
|
||||
Declare a new function with record syntax
|
||||
|
||||
Being this data type:
|
||||
data Color = C { red,
|
||||
, blue
|
||||
, yellow :: Int }
|
||||
|
||||
It can only be match on blue only:
|
||||
|
||||
isBlueZero (C { blue = 0 }) = True
|
||||
isBlueZero _ = False
|
||||
|
||||
Defining a PixelColor type and a function replace values with non-zero blue components.
|
||||
|
||||
Where and let
|
||||
|
||||
Let must always be followed by in. The in must appear in the sale column as the let keyword.
|
||||
In the following example, mult multiples its argument n by x, which passed to the original multiples.
|
||||
multiples x =
|
||||
let mult n = n * x
|
||||
in map mult [1..10]
|
||||
|
||||
|
||||
Where is similar to let. The scope of a where definition is the current function.
|
||||
In the following example, the function result below has a different meaning depending on the arguments given to the function strlen:
|
||||
strlen [] = result
|
||||
where result = "No string given!"
|
||||
strlen f = result ++ " characters long!"
|
||||
where result = show (length f)
|
||||
|
||||
|
||||
It is important to know that let ... in ... is an expression, that is, it can be written wherever expressions are allowed.
|
||||
In contrast, where is bound to a surrounding syntactic construct, like the pattern matching line of a function definition.
|
||||
|
||||
Advantage of where
|
||||
Suppose you have the function
|
||||
f :: s -> (a,s)
|
||||
f x = y
|
||||
where y = ... x ...
|
||||
and later you decide to put this into the Control.Monad.State monad.
|
||||
|
||||
However, transforming to
|
||||
f :: State s a
|
||||
f = State $ \x -> y
|
||||
where y = ... x ...
|
||||
will not work, because where refers to the pattern matching f =, where no x is in scope. In contrast, if you had started with let, then you wouldn't have trouble.
|
||||
f :: s -> (a,s)
|
||||
f x =
|
||||
let y = ... x ...
|
||||
in y
|
||||
|
||||
This is easily transformed to:
|
||||
f :: State s a
|
||||
f = State $ \x ->
|
||||
let y = ... x ...
|
||||
in y
|
||||
|
||||
Advantage of let
|
||||
|
||||
Because "where" blocks are bound to a syntactic construct, they can be used to share bindings between parts of a function that are not syntactically expressions.
|
||||
For example:
|
||||
f x
|
||||
| cond1 x = a
|
||||
| cond2 x = g a
|
||||
| otherwise = f (h x a)
|
||||
where
|
||||
a = w x
|
||||
|
||||
In expression style, you might use an explicit case:
|
||||
f x
|
||||
= let a = w x
|
||||
in case () of
|
||||
_ | cond1 x -> a
|
||||
| cond2 x -> g a
|
||||
| otherwise -> f (h x a)
|
||||
|
||||
or a functional equivalent:
|
||||
f x =
|
||||
let a = w x
|
||||
in select (f (h x a))
|
||||
[(cond1 x, a),
|
||||
(cond2 x, g a)]
|
||||
or a series of if-then-else expressions:
|
||||
f x
|
||||
= let a = w x
|
||||
in if cond1 x
|
||||
then a
|
||||
else if cond2 x
|
||||
then g a
|
||||
|
||||
|
||||
Anonymous Functions
|
||||
|
||||
They are functions without names and can be defined at any time like so.
|
||||
Example: \x -> x + 1
|
||||
|
||||
Case expressions
|
||||
|
||||
case is to a switch statement in C# and Java. However, it can match a pattern.
|
||||
Example:
|
||||
data Choices = First String | Second | Third | Fourth
|
||||
|
||||
case can be used to determine which choice was given
|
||||
|
||||
whichChoice ch =
|
||||
case ch of
|
||||
First _ -> "1st!"
|
||||
Second -> "2nd!"
|
||||
_ -> "Something else."
|
||||
|
||||
|
||||
Conditionals
|
||||
|
||||
Identify ==
|
||||
Non identify /n
|
||||
Comparatives where the type must a subclass of Ord <,>,<=,>=
|
||||
|
||||
The if statement has this “signature”: if-then-else :: Bool -> a -> a -> a
|
||||
|
||||
Maps and filters
|
||||
|
||||
map takes a function and a list and applies that function to every element in the list, producing a new list.
|
||||
Examples:
|
||||
map :: (a -> b) -> [a] -> [b]
|
||||
map _ [] = []
|
||||
map f (x:xs) = f x : map f xs
|
||||
|
||||
filter is a function that takes a predicate and nd a list and then returns the list of elements that satisfy the predicate
|
||||
Examples:
|
||||
filter :: (a -> Bool) -> [a] -> [a]
|
||||
filter _ [] = []
|
||||
filter p (x:xs)
|
||||
| p x = x : filter p xs
|
||||
| otherwise = filter p xs
|
||||
|
||||
Folds
|
||||
|
||||
foldl function folds the list up from the left side.
|
||||
foldr works in a similar way to the left fold, only the accumulator eats up the values from the right.
|
||||
|
||||
The foldl1 and foldr1 functions work much like foldl and foldr, only you don't need to provide them with an explicit starting value.
|
||||
|
||||
scanl and scanr are like foldl and foldr, only they report all the intermediate accumulator states in the form of a list.
|
||||
|
||||
Function application with $
|
||||
|
||||
The $ function has the lowest precedence and the function with $ is rigth-associate
|
||||
|
||||
Default
|
||||
|
||||
Default implementations can be given for function in a class.
|
||||
|
||||
The default is defined by giving a body to one of the members' functions.
|
||||
Example == can be defined in terms of /=:
|
||||
(==) a b = not (a/b)
|
||||
|
||||
Data
|
||||
|
||||
Algebraic data types can be declared as: data MyType = MyValue1 | MyValue2
|
||||
|
||||
Note that type and constructor names must start with a capital letter. It is a syntax error otherwise.
|
||||
|
||||
|
||||
Constructors with arguments
|
||||
|
||||
Constructors that take arguments can be declared, allowing more information to be stored.
|
||||
|
||||
data Point = TwoD Int Int
|
||||
| ThreeD Int Int Int
|
||||
|
||||
Notice that the arguments for each constructor are type names, not constructors.
|
||||
|
||||
Type and constructor names
|
||||
|
||||
Both names can be the same since they will never be used in a place that would cause confusion.
|
||||
data User = User String | Admin String
|
||||
|
||||
Using this type in a function makes difference clear:
|
||||
whatUser (User _) = "normal user"
|
||||
whatUser (Admin _) = "admin user"
|
||||
|
||||
Type Variables
|
||||
|
||||
Plymorphic data types are easy to be declared just by adding type varialbe in the declaration:
|
||||
data Slot a = Slot1 a | Empty1
|
||||
|
||||
It can also be mix type variable and specific types in constructors:
|
||||
data Slot2 a = Slot2 a Int | Empty2
|
||||
|
||||
Record syntax
|
||||
|
||||
Constructors arguments can also be declared by using record syntax which gives a name to each argument.
|
||||
For example:
|
||||
data Contact = Contact { ctName :: String
|
||||
, ctEmail :: String
|
||||
, ctPhone :: String }
|
||||
|
||||
Note: Multiple constructors of the same type can use the same accessor function name for values of the same type.
|
||||
|
||||
Deriving
|
||||
|
||||
The capabilities to convert to and from strings, compare
|
||||
for equality, or order in a sequence are defined as Typeclasses and Haskell provides the deriving keyboard to automatically implement the typeclass on the associated type supported which are: Eq, Read, Show, Ord, Enum, Ix, and
|
||||
Bounded.
|
||||
|
||||
Two forms of deriving are possible.
|
||||
|
||||
The first is used when a type only derives one class:
|
||||
data Priority = Low | Medium | High
|
||||
deriving Show
|
||||
|
||||
The second is used when multiple classes are derived:
|
||||
data Alarm = Soft | Loud | Deafening
|
||||
deriving (Read, Show)
|
||||
|
||||
Class constraint
|
||||
|
||||
In any case, the syntax used is:
|
||||
data (Num a) => SomeNumber a = Two a a
|
||||
| Three a a a
|
||||
|
||||
This declares a type SomeNumber which has one type variable argument.
|
||||
Valid types are those in the Num class.
|
||||
|
||||
Do
|
||||
|
||||
Do indicates that the code to follow will be in a monadic context.
|
||||
Statements are separated by newlines, the assignment is indicated by <, and a let form is introduced which does not require the in the keyboard.
|
||||
|
||||
If, Then, Else
|
||||
|
||||
This function tests if the string is given starts with a lower case letter and, if so, convert it to upper case:
|
||||
|
||||
sentenceCase (s:rest) =
|
||||
if isLower s
|
||||
then toUpper s : rest
|
||||
else s : result
|
||||
sentenceCase _ = []
|
||||
|
||||
Deconstruction
|
||||
|
||||
The left-hand side of a let definition can also destructive its argument, in case sub-components are to be accessed.
|
||||
Examples:
|
||||
firstThree str =
|
||||
let (a:b:c:_) = str
|
||||
in "Initial three characters are: " ++
|
||||
show a ++ ", " ++
|
||||
show b ++ ", and " ++
|
||||
show c
|
||||
|
||||
Note that this is different than the following, which only works if the string has exactly three characters:
|
||||
onlyThree str =
|
||||
let (a:b:c:[]) = str
|
||||
in "The characters given are: " ++
|
||||
show a ++ ", " ++
|
||||
show b ++ ", and " ++
|
||||
show c
|
||||
|
||||
Modules
|
||||
|
||||
A module is a compilation unit which export functions, tyñes, classes, instances, and other modules.
|
||||
To make a Haskell file a module just add at the top of it:
|
||||
module MyModule where
|
||||
|
||||
Imports
|
||||
|
||||
To import everything (functions, data types and constructors, class declarations, and even other modules imported) exported by a library, just use the module name:
|
||||
import Text.Read
|
||||
|
||||
To import selectively:
|
||||
import Text.Read (readParen, lex)
|
||||
|
||||
To import data types and no constructors:
|
||||
import Text.Read (Lexeme)
|
||||
|
||||
To import data types and one or more constructors explicitly
|
||||
import Text.Read (Lexeme(Ident, Symbol))
|
||||
|
||||
To import all constructors for a given type:
|
||||
import Text.Read (Lexeme())
|
||||
Reference in New Issue
Block a user