Difference between revisions of "Keywords"

From HaskellWiki
Jump to navigation Jump to search
(→‎{-, -}: space is important)
m
 
(66 intermediate revisions by 20 users not shown)
Line 1: Line 1:
 
This page lists all Haskell keywords, feel free to edit. [[Hoogle]] searches will return results from this page. Please respect the Anchor macros.
 
This page lists all Haskell keywords, feel free to edit. [[Hoogle]] searches will return results from this page. Please respect the Anchor macros.
   
For additional information you might want to look at [http://www.haskell.org/onlinereport/ the Haskell 98 report].
+
For additional information you might want to look at [http://www.haskell.org/onlinereport/haskell2010/ the Haskell 2010 report].
   
=== . ===
+
== ! ==
   
  +
Whenever a data [[constructor]] is applied, each argument to the
The dot "." is used to compose functions in point-free style, similar to "$".
 
  +
constructor is evaluated if and only if the corresponding type in the
  +
algebraic data[[type]] declaration has a strictness flag, denoted by an
  +
exclamation point. For example:
   
<haskell>foo = h . g . f</haskell>
 
is the same as
 
<haskell>foo x = h $ g $ f x</haskell>
 
which is the same as
 
<haskell>foo x = h (g (f x))</haskell>
 
 
 
== ` ==
 
 
A function enclosed in back ticks "`" can be used as an infix operator.
 
 
<haskell>2 `subtract` 10</haskell>
 
is the same as
 
<haskell>subtract 2 10</haskell>
 
 
== | ==
 
 
The "pipe" is used in several places
 
 
* Data type definitions, "or"
 
 
<haskell>
 
<haskell>
data Maybe a = Just a | Nothing
+
data STList a
  +
= STCons a !(STList a) -- the second argument to STCons will be
  +
-- evaluated before STCons is applied
  +
| STNil
 
</haskell>
 
</haskell>
   
  +
to illustrate the difference between strict versus lazy constructor
* List comprehensions, "where"
 
  +
application, consider the following:
<haskell>
 
squares = [a*a | a <- [1..]]
 
</haskell>
 
   
* Guards, "when"
 
 
<haskell>
 
<haskell>
  +
stList = STCons 1 undefined
safeTail x | null x = []
 
  +
lzList = (:) 1 undefined
| otherwise = tail x
 
  +
stHead (STCons h _) = h -- this evaluates to undefined when applied to stList
  +
lzHead (h : _) = h -- this evaluates to 1 when applied to lzList
 
</haskell>
 
</haskell>
   
  +
! is also used in the [https://downloads.haskell.org/~ghc/7.8.4/docs/html/users_guide/bang-patterns.html "bang patterns"] (GHC extension), to indicate
* [[Functional dependencies]]
 
  +
strictness in patterns:
  +
 
<haskell>
 
<haskell>
  +
f !x !y = x + y
-- This examples assumes that each type 'c' can "contain" only one type
 
class Contains c elt | c -> elt where
 
...
 
 
 
</haskell>
 
</haskell>
   
  +
== ' ==
  +
* Character literal: <hask>'a'</hask>
  +
* [[Template Haskell]]: Name of a (value) variable or data constructor: <hask>'length</hask>, <hask>'Left</hask>
  +
* (in types, GHC specific) Promoted data constructor: <hask>'True</hask>
   
== \ ==
+
== <nowiki>''</nowiki> ==
  +
* [[Template Haskell]]: Name of a type constructor or class: <hask>''Int</hask>, <hask>''Either</hask>, <hask>''Show</hask>
The backslash "\" is used
 
 
* in multiline strings
 
* in lambda functions
 
<haskell>
 
\x -> x + 1
 
</haskell>
 
   
 
== - ==
 
== - ==
 
This operator token is magic/irregular in the sense that
 
This operator token is magic/irregular in the sense that
 
<haskell>(- 1)</haskell>
 
<haskell>(- 1)</haskell>
is parsed as the negative integer -1, rather than as an operator [[section]], as it would be for any other operator:
+
is parsed as the negative integer -1, rather than as an operator [[Section of an infix operator|section]], as it would be for any other operator:
 
<haskell>(* 1) :: Num a => a -> a</haskell>
 
<haskell>(* 1) :: Num a => a -> a</haskell>
 
<haskell>(++ "foo") :: String -> String</haskell>
 
<haskell>(++ "foo") :: String -> String</haskell>
   
  +
It is syntactic sugar for the <hask>negate</hask> function in Prelude. See [[unary operator]].
 
If you want the section, you can use the <hask>subtract</hask> function.
+
If you want the section, you can use the <hask>subtract</hask> function or <hask>(+(-1))</hask>.
   
 
== -- ==
 
== -- ==
Line 84: Line 66:
   
 
== -< ==
 
== -< ==
  +
[http://downloads.haskell.org/~ghc/latest/docs/html/users_guide/glasgow_exts.html#arrow-notation Arrow notation]
[[Arrow notation]]
 
   
 
== -<< ==
 
== -<< ==
  +
[http://downloads.haskell.org/~ghc/latest/docs/html/users_guide/glasgow_exts.html#arrow-notation Arrow notation]
[[Arrow notation]]
 
 
   
 
== -> ==
 
== -> ==
Line 107: Line 88:
 
Nothing -> False
 
Nothing -> False
 
Just x -> True
 
Just x -> True
  +
</haskell>
  +
  +
or with LambdaCase:
  +
<haskell>
  +
(\ case 1 -> 0
  +
; _ -> 1 )
  +
</haskell>
  +
  +
or with MultiWayIf:
  +
<haskell>
  +
if | 1 == 0 -> 1
  +
| 1 == 2 -> 2
  +
| otherwise -> 3
 
</haskell>
 
</haskell>
   
 
* On the kind level (GHC specific):
 
* On the kind level (GHC specific):
 
<haskell>
 
<haskell>
(->) :: ?? -> ? -> *
+
ghci> :kind (->)
  +
(->) :: * -> * -> *
 
</haskell>
 
</haskell>
   
Line 117: Line 112:
 
<haskell>
 
<haskell>
 
-- This examples assumes that each type 'c' can "contain" only one type
 
-- This examples assumes that each type 'c' can "contain" only one type
  +
-- i.e. type 'c' uniquely determines type 'elt'
 
class Contains c elt | c -> elt where
 
class Contains c elt | c -> elt where
 
...
 
...
  +
</haskell>
   
  +
* [[View patterns]]
  +
  +
== :: ==
  +
  +
Read as "has type":
  +
  +
<haskell>
  +
length :: [a] -> Int
 
</haskell>
 
</haskell>
  +
  +
"Length has type list-of-'a' to Int"
  +
  +
Or "has kind" (GHC specific):
  +
  +
<haskell>
  +
Either :: * -> * -> *
  +
</haskell>
  +
  +
== ; ==
  +
* Statement separator in an explicit block (see [[layout]])
   
 
== <- ==
 
== <- ==
Line 130: Line 146:
 
</haskell>
 
</haskell>
   
* In list comprehension generators, "is drawn from":
+
* In list comprehension generators, "in":
 
<haskell>
 
<haskell>
 
[ (x,y) | x <- [1..10], y <- ['a'..'z'] ]
 
[ (x,y) | x <- [1..10], y <- ['a'..'z'] ]
 
</haskell>
 
</haskell>
   
* In [[pattern guard | pattern guards]], "matches":
+
* In [[pattern guard]]s, "matches":
 
<haskell>
 
<haskell>
 
f x y | Just z <- g x = True
 
f x y | Just z <- g x = True
Line 141: Line 157:
 
</haskell>
 
</haskell>
   
== @ ==
+
== , ==
  +
  +
Separator in lists, tuples, records.
   
Patterns of the form var@pat are called as-patterns, and allow one to
 
use var as a name for the value being matched by pat. For example:
 
 
<haskell>
 
<haskell>
  +
[1,2,3]
case e of { xs@(x:rest) -> if x==0 then rest else xs }
 
  +
(1,2,3)
  +
Point {x = 1, y = 2}
 
</haskell>
 
</haskell>
   
  +
In list comprehensions before generators, "and" (the first comma after <code>|</code>):
is equivalent to:
 
  +
<haskell>
  +
[ (x,y) | x <- [1..10], y <- ['a'..'z'], x > 42 ]
  +
</haskell>
   
  +
In list comprehensions before Boolean tests, "when" (the second comma after <code>|</code>):
 
<haskell>
 
<haskell>
  +
[ (x,y) | x <- [1..10], y <- ['a'..'z'], x > 42 ]
let { xs = e } in
 
case xs of { (x:rest) -> if x==0 then rest else xs }
 
 
</haskell>
 
</haskell>
   
  +
In guards inside case expressions, "and when":
== $ ==
 
  +
<haskell>
  +
case [1,3,9] of xs | (x:ys) <- xs, (y:_) <- ys, let z=x+1, z /= y -> [x,y,z]
  +
</haskell>
   
  +
In module import and export lists:
The dollar sign "$" is a way to compose functions, without typing too many brackets.
 
   
<haskell>foo x = h $ g $ f x</haskell>
+
<haskell>
  +
module MyModule
is the same as
 
  +
( MyData (C1,C2)
<haskell>foo x = h (g (f x))</haskell>
 
  +
, myFun ) where
   
  +
import MyModule (MyData (C1,C2), myFun)
  +
</haskell>
   
== ! ==
+
== = ==
  +
Used in definitions.
   
  +
<haskell>
Whenever a data [[constructor]] is applied, each argument to the
 
  +
x = 4
constructor is evaluated if and only if the corresponding type in the
 
  +
</haskell>
algebraic data[[type]] declaration has a strictness flag, denoted by an
 
  +
exclamation point. For example:
 
  +
Also in pattern-matching records:
   
 
<haskell>
 
<haskell>
  +
case point of
data STList a
 
  +
Point {x = x0, y = y0} -> f x0 y0
= STCons a !(STList a) -- the second argument to STCons will be
 
-- evaluated before STCons is applied
 
| STNil
 
 
</haskell>
 
</haskell>
   
  +
== => ==
to illustrate the difference between strict versus lazy constructor
 
  +
application, consider the following:
 
  +
Used to indicate instance contexts, for example:
   
 
<haskell>
 
<haskell>
  +
sort :: Ord a => [a] -> [a]
stList = STCons 1 undefined
 
lzList = (:) 1 undefined
 
stHead (STCons h _) = h -- this evaluates to undefined when applied to stList
 
lzHead (h : _) = h -- this evaluates to 1 when applied to lzList
 
 
</haskell>
 
</haskell>
   
  +
== > ==
! is also used in the [http://www.haskell.org/ghc/docs/latest/html/users_guide/bang-patterns.html "bang patterns"] (GHC extension), to indicate
 
  +
strictness in patterns:
 
  +
In a Bird's style [[Literate_programming|Literate Haskell file]], the > character is used to introduce a code line.
   
 
<haskell>
 
<haskell>
  +
comment line
f !x !y = x + y
 
  +
  +
> main = print "hello world"
 
</haskell>
 
</haskell>
   
  +
== ? ==
Finally, it is the array subscript operator:
 
  +
  +
* {{GHCUsersGuide|exts/implicit_parameters||a section about Implicit Parameters}}
  +
 
<haskell>
 
<haskell>
  +
ghci> :t ?foo ++ "bar"
let x = arr ! 10
 
  +
?foo ++ "bar" :: (?foo::[Char]) => [Char]
 
</haskell>
 
</haskell>
   
== : ==
+
== # ==
   
  +
* [https://downloads.haskell.org/~ghc/7.6.2/docs/html/users_guide/syntax-extns.html MagicHash]
The colon ":" is an infix operator that adds an element to the beginning of a list.
 
   
  +
== * ==
<haskell>1 : [2,3]</haskell>
 
will result in the new list
 
<haskell>[1,2,3]</haskell>
 
   
  +
* Is an ordinary operator name on the value level
== :: ==
 
   
  +
* On the [[kind]] level: The kind of boxed types (GHC-specific)
Read as "has type":
 
   
 
<haskell>
 
<haskell>
length :: [a] -> Int
+
ghci> :kind Int
  +
Int :: *
  +
</haskell>
  +
  +
== @ ==
  +
  +
* Patterns of the form <hask>var@pat</hask> are called as-patterns, and allow one to use <hask>var</hask> as a name for the value being matched by <hask>pat</hask>. For example:
  +
<haskell>
  +
case e of { xs@(x:rest) -> if x==0 then rest else xs }
  +
  +
-- is equivalent to:
  +
  +
let { xs = e } in
  +
case xs of { (x:rest) -> if x==0 then rest else xs }
  +
</haskell>
  +
  +
* [https://ghc.gitlab.haskell.org/ghc/doc/users_guide/exts/type_applications.html#visible-type-application Visible type applications]
  +
  +
== [|, |] ==
  +
* [[Template Haskell]]
  +
** Expression quotation: <hask> [| print 1 |] </hask>
  +
** Declaration quotation: <hask> [d| main = print 1 |] </hask>
  +
** Type quotation: <hask> [t| Either Int () |] </hask>
  +
** Pattern quotation: <hask> [p| (x,y) |] </hask>
  +
** [[Quasiquotation]]: <hask> [nameOfQuasiQuoter| ... |] </hask>
  +
  +
== \ ==
  +
The backslash "\" is used
  +
  +
* in multiline strings
  +
<haskell>
  +
"foo\
  +
\bar"
  +
</haskell>
  +
  +
* in lambda functions
  +
<haskell>
  +
\x -> x + 1
 
</haskell>
 
</haskell>
   
"Length has type list-of-'a' to Int"
 
   
 
== _ ==
 
== _ ==
Line 235: Line 301:
 
</haskell>
 
</haskell>
   
== ~ ==
 
   
Lazy pattern bindings. Matching the pattern ~pat against a value always
 
suceeds, and matching will only diverge when one of the variables bound
 
in the pattern is used.
 
   
<haskell>
 
f1,f2 :: Maybe Int -> String;
 
(+++),(++++) :: (a->b)->(c->d)->(a,c)->(b,d);
 
 
f1 x = case x of {Just n -> "Got it"};
 
f2 x = case x of {~(Just n) -> "Got it"};
 
 
(f +++ g) ~(x,y) = (f x , g y);
 
(f ++++ g) (x,y) = (f x , g y);
 
</haskell>
 
   
Then we have:
 
   
  +
== ` ==
<haskell>
 
f1 Nothing
 
Exception: Non-exhaustive patterns in case
 
   
  +
A function enclosed in back ticks "`" can be used as an infix operator.
f2 Nothing
 
"Got it"
 
   
  +
<haskell>2 `subtract` 10</haskell>
(const 1 +++ const 2) undefined
 
  +
is the same as
(1,2)
 
  +
<haskell>subtract 2 10</haskell>
 
(const 1 ++++ const 2) undefined
 
Exception: Prelude.undefined
 
</haskell>
 
 
For more details see [http://en.wikibooks.org/wiki/Haskell/Laziness#Lazy_pattern_matching the Haskell Wikibook].
 
 
== > ==
 
 
In a Bird's style [[Literate_programming|Literate Haskell file]], the > character is used to introduce a code line.
 
 
<haskell>
 
comment line
 
 
> main = print "hello world"
 
</haskell>
 
   
 
== {, } ==
 
== {, } ==
* Explicit block (disable [[layout]])
+
* Explicit block (disable [[layout]]), possibly with ";" .
   
 
* Record update notation
 
* Record update notation
Line 302: Line 335:
 
</haskell>
 
</haskell>
   
== ; ==
+
== | ==
  +
* Statement separator in an explicit block (see [[layout]])
 
  +
The "pipe" is used in several places
  +
  +
* Data type definitions, "or"
  +
<haskell>
  +
data Maybe a = Just a | Nothing
  +
</haskell>
  +
  +
* List comprehensions, "for" (as in, "list of <code>a*a</code> for <code>a</code> in <code>[1..]</code>)
  +
<haskell>
  +
squares = [a*a | a <- [1..]]
  +
</haskell>
  +
  +
* Guards, "when"
  +
<haskell>
  +
safeTail x | null x = []
  +
| otherwise = tail x
  +
</haskell>
  +
  +
* [[Functional dependencies]], "where"
  +
<haskell>
  +
class Contains c elt | c -> elt where
  +
...
  +
</haskell>
  +
  +
== ~ ==
  +
  +
* Lazy pattern bindings. Matching the pattern <hask>~pat</hask> against a value always succeeds, and matching will only diverge when one of the variables bound in the pattern is used.
  +
  +
<haskell>
  +
f1, f2 :: Maybe Int -> String
  +
f1 x = case x of
  +
Just n -> "Got it"
  +
f2 x = case x of
  +
~(Just n) -> "Got it"
  +
  +
(+++), (++++) :: (a -> b) -> (c -> d) -> (a, c) -> (b, d)
  +
(f +++ g) ~(x, y) = (f x, g y)
  +
(f ++++ g) (x, y) = (f x, g y)
  +
</haskell>
  +
  +
Then we have:
  +
  +
<haskell>
  +
f1 Nothing
  +
Exception: Non-exhaustive patterns in case
  +
  +
f2 Nothing
  +
"Got it"
  +
  +
(const 1 +++ const 2) undefined
  +
(1,2)
  +
  +
(const 1 ++++ const 2) undefined
  +
Exception: Prelude.undefined
  +
</haskell>
  +
  +
For more details see [http://en.wikibooks.org/wiki/Haskell/Laziness#Lazy_pattern_matching the Haskell Wikibook].
  +
  +
* Equality constraints. Assert that two types in a context must be the same:
  +
  +
<haskell>
  +
example :: F a ~ b => a -> b
  +
</haskell>
  +
  +
Here the type "F a" must be the same as the type "b", which allows one to constrain polymorphism (especially where type families are involved), but to a lesser extent than functional dependencies. See [[Type_families#Equality_constraints|Type Families]].
   
 
== as ==
 
== as ==
Line 326: Line 424:
   
 
<haskell>
 
<haskell>
| g1 -> e1
+
| g1 -> e1
...
+
...
| gm -> em
+
| gm -> em
where decls
+
where decls
 
</haskell>
 
</haskell>
   
Line 473: Line 571:
 
== forall ==
 
== forall ==
   
This is a GHC/Hugs extension, and as such is not portable Haskell 98.
+
This is a GHC/Hugs extension, and as such is not portable Haskell 98/2010.
 
It is only a reserved word within types.
 
It is only a reserved word within types.
   
 
Type variables in a Haskell type expression are all assumed to be
 
Type variables in a Haskell type expression are all assumed to be
 
universally quantified; there is no explicit syntax for universal
 
universally quantified; there is no explicit syntax for universal
quantification, in standard Haskell 98. For example, the type expression
+
quantification, in standard Haskell 98/2010. For example, the type expression
 
<hask>a -> a</hask> denotes the type <hask>forall a. a ->a</hask>.
 
<hask>a -> a</hask> denotes the type <hask>forall a. a ->a</hask>.
 
For clarity, however, we often write quantification explicitly when
 
For clarity, however, we often write quantification explicitly when
Line 492: Line 590:
 
</haskell>
 
</haskell>
   
GHC [http://www.haskell.org/ghc/docs/latest/html/users_guide/data-type-extensions.html#type-synonyms introduces] a <hask>forall</hask> keyword, allowing explicit quantification, for example, to encode
+
GHC [https://downloads.haskell.org/~ghc/latest/docs/html/users_guide/exts/poly_kinds.html#inferring-dependency-in-user-written-foralls introduces] a <hask>forall</hask> keyword, allowing explicit quantification, for example, to encode
[http://www.haskell.org/ghc/docs/latest/html/users_guide/data-type-extensions.html#existential-quantification existential types]:
+
[http://downloads.haskell.org/~ghc/latest/docs/html/users_guide/exts/existential_quantification.html existential types]:
 
<haskell>
 
<haskell>
 
data Foo = forall a. MkFoo a (a -> Bool)
 
data Foo = forall a. MkFoo a (a -> Bool)
Line 563: Line 661:
 
the fixity and binding precedence of one or more operators. The integer
 
the fixity and binding precedence of one or more operators. The integer
 
in a fixity declaration must be in the range 0 to 9. A fixity
 
in a fixity declaration must be in the range 0 to 9. A fixity
declaration may appear anywhere that a type signature appears and, like
+
declaration may appear anywhere that a [[type signature]] appears and, like
 
a type signature, declares a property of a particular operator.
 
a type signature, declares a property of a particular operator.
   
Line 595: Line 693:
 
<haskell>let { d1 ; ... ; dn } in e</haskell>
 
<haskell>let { d1 ; ... ; dn } in e</haskell>
   
They introduce a nested, lexically-scoped, mutually-recursive list of declarations (let is often called letrec in other languages). The scope of the declarations is the expression e and the right hand side of the declarations.
+
They introduce a nested, lexically-scoped, mutually-recursive list of declarations (let is often called [https://en.wikipedia.org/wiki/Let_expression let rec] in other languages). The scope of the declarations is the expression e and the right hand side of the declarations.
   
Within <hask>do</hask>-blocks or list comprehensions <hask>let { d1 ; ... ; dn }</hask> without <hask>in</hask> serves to indroduce local bindings.
+
Within <hask>do</hask>-blocks or list comprehensions <hask>let { d1 ; ... ; dn }</hask> without <hask>in</hask> serves to introduce local bindings.
   
== [http://www.haskell.org/ghc/docs/latest/html/users_guide/syntax-extns.html#id3017137 mdo] ==
+
== [https://downloads.haskell.org/ghc/9.4.4/docs/users_guide/exts/recursive_do.html#the-mdo-notation mdo] ==
   
The recursive <hask>do</hask> keyword enabled by -fglasgow-exts
+
The recursive <hask>do</hask> keyword enabled by -fglasgow-exts.
   
 
== module ==
 
== module ==
Line 627: Line 725:
 
newtype FunctionIdentifier = FunctionIdentifier Identifier
 
newtype FunctionIdentifier = FunctionIdentifier Identifier
   
Most often, one supplies [[smart constructors]] and [[destructor]]s for these to ease working with them.
+
Most often, one supplies [[smart constructors]] and [[smart destructors|destructors]] for these to ease working with them.
   
 
See the page on [[type]]s for more information, links and examples.
 
See the page on [[type]]s for more information, links and examples.
Line 634: Line 732:
   
 
== proc ==
 
== proc ==
  +
proc (arrow abstraction)
  +
is a kind of lambda, except that it constructs an arrow instead of a function.
  +
 
[[Arrow notation]]
 
[[Arrow notation]]
   
Line 657: Line 758:
   
 
== rec ==
 
== rec ==
The [http://www.haskell.org/ghc/docs/latest/html/users_guide/syntax-extns.html#mdo-notation rec] keyword can be used when the <code>-XDoRec</code> flag is given; it allows recursive bindings in a do-block.
+
The [https://downloads.haskell.org/ghc/9.4.4/docs/users_guide/exts/recursive_do.html#the-mdo-notation rec] keyword can be used when the <code>-XDoRec</code> flag is given; it allows recursive bindings in a do-block.
   
 
<haskell>
 
<haskell>
Line 699: Line 800:
 
== where ==
 
== where ==
   
Used to introduce a module, instance or class:
+
Used to introduce a module, instance, class or [[GADT]]:
 
<haskell>
 
<haskell>
 
module Main where
 
module Main where
Line 708: Line 809:
 
instance Num Int where
 
instance Num Int where
 
...
 
...
  +
  +
data Something a where
  +
...
 
</haskell>
 
</haskell>
   
Line 719: Line 823:
 
</haskell>
 
</haskell>
   
  +
[[Category: Glossary]]
 
 
[[Category:Language]]
 
[[Category:Language]]

Latest revision as of 04:31, 8 June 2023

This page lists all Haskell keywords, feel free to edit. Hoogle searches will return results from this page. Please respect the Anchor macros.

For additional information you might want to look at the Haskell 2010 report.

!

Whenever a data constructor is applied, each argument to the constructor is evaluated if and only if the corresponding type in the algebraic datatype declaration has a strictness flag, denoted by an exclamation point. For example:

 data STList a 
         = STCons a !(STList a)  -- the second argument to STCons will be 
                                 -- evaluated before STCons is applied
         | STNil

to illustrate the difference between strict versus lazy constructor application, consider the following:

 stList = STCons 1 undefined
 lzList = (:)    1 undefined
 stHead (STCons h _) = h -- this evaluates to undefined when applied to stList
 lzHead (h : _)      = h -- this evaluates to 1 when applied to lzList

! is also used in the "bang patterns" (GHC extension), to indicate strictness in patterns:

f !x !y = x + y

'

  • Character literal: 'a'
  • Template Haskell: Name of a (value) variable or data constructor: 'length, 'Left
  • (in types, GHC specific) Promoted data constructor: 'True

''

-

This operator token is magic/irregular in the sense that

(- 1)

is parsed as the negative integer -1, rather than as an operator section, as it would be for any other operator:

(* 1) :: Num a => a -> a
(++ "foo") :: String -> String

It is syntactic sugar for the negate function in Prelude. See unary operator. If you want the section, you can use the subtract function or (+(-1)).

--

Starts a single-line comment, unless immediately followed by an operator character other than -:

main = print "hello world" -- this is a comment
--this is a comment as well
---this too
foobar --+ this_is_the_second_argument_of_the_dash_dash_plus_operator

The multi-line variant for comments is {- comment -}.

-<

Arrow notation

-<<

Arrow notation

->

  • The function type constructor:
length :: [a] -> Int
  • In lambda functions:
\x -> x + 1
  • To denote alternatives in case statements:
case Just 3 of
    Nothing -> False
    Just x  -> True

or with LambdaCase:

(\ case 1 -> 0
      ; _ -> 1 )

or with MultiWayIf:

if | 1 == 0    -> 1 
   | 1 == 2    -> 2 
   | otherwise -> 3
  • On the kind level (GHC specific):
ghci> :kind (->)
(->) :: * -> * -> *
-- This examples assumes that each type 'c' can "contain" only one type
--  i.e. type 'c' uniquely determines type 'elt'
class Contains c elt | c -> elt where
   ...

::

Read as "has type":

length :: [a] -> Int

"Length has type list-of-'a' to Int"

Or "has kind" (GHC specific):

Either :: * -> * -> *

;

  • Statement separator in an explicit block (see layout)

<-

  • In do-notation, "draw from":
do x <- getChar
   putChar x
  • In list comprehension generators, "in":
[ (x,y) | x <- [1..10], y <- ['a'..'z'] ]
f x y | Just z <- g x = True
      | otherwise     = False

,

Separator in lists, tuples, records.

[1,2,3]
(1,2,3)
Point {x = 1, y = 2}

In list comprehensions before generators, "and" (the first comma after |):

[ (x,y) | x <- [1..10], y <- ['a'..'z'], x > 42 ]

In list comprehensions before Boolean tests, "when" (the second comma after |):

[ (x,y) | x <- [1..10], y <- ['a'..'z'], x > 42 ]

In guards inside case expressions, "and when":

case [1,3,9] of xs | (x:ys) <- xs, (y:_) <- ys, let z=x+1, z /= y -> [x,y,z]

In module import and export lists:

module MyModule
  ( MyData (C1,C2)
  , myFun ) where

import MyModule (MyData (C1,C2), myFun)

=

Used in definitions.

x = 4

Also in pattern-matching records:

case point of
  Point {x = x0, y = y0} -> f x0 y0

=>

Used to indicate instance contexts, for example:

sort :: Ord a => [a] -> [a]

>

In a Bird's style Literate Haskell file, the > character is used to introduce a code line.

comment line

> main = print "hello world"

?

ghci> :t ?foo ++ "bar"
?foo ++ "bar" :: (?foo::[Char]) => [Char]

#

*

  • Is an ordinary operator name on the value level
  • On the kind level: The kind of boxed types (GHC-specific)
ghci> :kind Int
Int :: *

@

  • Patterns of the form var@pat are called as-patterns, and allow one to use var as a name for the value being matched by pat. For example:
     case e of { xs@(x:rest) -> if x==0 then rest else xs }

    -- is equivalent to:

     let { xs = e } in
       case xs of { (x:rest) -> if x==0 then rest else xs }

[|, |]

  • Template Haskell
    • Expression quotation: [| print 1 |]
    • Declaration quotation: [d| main = print 1 |]
    • Type quotation: [t| Either Int () |]
    • Pattern quotation: [p| (x,y) |]
    • Quasiquotation: [nameOfQuasiQuoter| ... |]

\

The backslash "\" is used

  • in multiline strings
"foo\
  \bar"
  • in lambda functions
\x -> x + 1


_

Patterns of the form _ are wildcards and are useful when some part of a pattern is not referenced on the right-hand-side. It is as if an identifier not used elsewhere were put in its place. For example,

 case e of { [x,_,_]  ->  if x==0 then True else False }

is equivalent to:

 case e of { [x,y,z]  ->  if x==0 then True else False }



`

A function enclosed in back ticks "`" can be used as an infix operator.

2 `subtract` 10

is the same as

subtract 2 10

{, }

  • Explicit block (disable layout), possibly with ";" .
  • Record update notation
changePrice :: Thing -> Price -> Thing
changePrice x new = x { price = new }
  • Comments (see below)

{-, -}

Everything between "{-" followed by a space and "-}" is a block comment.

{-
hello
world
-}

|

The "pipe" is used in several places

  • Data type definitions, "or"
data Maybe a = Just a | Nothing
  • List comprehensions, "for" (as in, "list of a*a for a in [1..])
squares = [a*a | a <- [1..]]
  • Guards, "when"
safeTail x | null x    = []
           | otherwise = tail x
class Contains c elt | c -> elt where
   ...

~

  • Lazy pattern bindings. Matching the pattern ~pat against a value always succeeds, and matching will only diverge when one of the variables bound in the pattern is used.
f1, f2 :: Maybe Int -> String
f1 x = case x of 
    Just n -> "Got it"
f2 x = case x of
    ~(Just n) -> "Got it"

(+++), (++++) :: (a -> b) -> (c -> d) -> (a, c) -> (b, d) 
(f +++ g) ~(x, y) = (f x, g y)
(f ++++ g) (x, y) = (f x, g y)

Then we have:

f1 Nothing
Exception: Non-exhaustive patterns in case

f2 Nothing
"Got it"

(const 1 +++ const 2) undefined
(1,2)

(const 1 ++++ const 2) undefined
Exception: Prelude.undefined

For more details see the Haskell Wikibook.

  • Equality constraints. Assert that two types in a context must be the same:
example :: F a ~ b => a -> b

Here the type "F a" must be the same as the type "b", which allows one to constrain polymorphism (especially where type families are involved), but to a lesser extent than functional dependencies. See Type Families.

as

Renaming module imports. Like qualified and hiding, as is not a reserved word but may be used as function or variable name.

import qualified Data.Map as M

main = print (M.empty :: M.Map Int ())

case, of

A case expression has the general form

 case e of { p1 match1 ; ... ; pn matchn }

where each matchi is of the general form

| g1 -> e1
  ...
| gm -> em
    where decls

Each alternative consists of patterns pi and their matches, matchi. Each matchi in turn consists of a sequence of pairs of guards gij and bodies eij (expressions), followed by optional bindings (declsi) that scope over all of the guards and expressions of the alternative. An alternative of the form

 pat -> exp where decls

is treated as shorthand for:

  pat | True -> exp
    where decls

A case expression must have at least one alternative and each alternative must have at least one body. Each body must have the same type, and the type of the whole expression is that type.

A case expression is evaluated by pattern matching the expression e against the individual alternatives. The alternatives are tried sequentially, from top to bottom. If e matches the pattern in the alternative, the guards for that alternative are tried sequentially from top to bottom, in the environment of the case expression extended first by the bindings created during the matching of the pattern, and then by the declsi  in the where clause associated with that alternative. If one of the guards evaluates to True, the corresponding right-hand side is evaluated in the same environment as the guard. If all the guards evaluate to False, matching continues with the next alternative. If no match succeeds, the result is _|_.

class

A class declaration introduces a new type class and the overloaded operations that must be supported by any type that is an instance of that class.

  class Num a  where
    (+)    :: a -> a -> a
    negate :: a -> a

data

The data declaration is how one introduces new algebraic data types into Haskell. For example:

data Set a = NilSet 
           | ConsSet a (Set a)

Another example, to create a datatype to hold an abstract syntax tree for an expression, one could use:

 data Exp = Ebin   Operator Exp Exp 
          | Eunary Operator Exp 
          | Efun   FunctionIdentifier [Exp] 
          | Eid    SimpleIdentifier

where the types Operator, FunctionIdentifier and SimpleIdentifier are defined elsewhere.

See the page on types for more information, links and examples.

data family

Declares a datatype family (see type families). GHC language extension.

data instance

Declares a datatype family instance (see type families). GHC language extension.


default

Ambiguities in the class Num are most common, so Haskell provides a way to resolve them---with a default declaration:

default (Int)

Only one default declaration is permitted per module, and its effect is limited to that module. If no default declaration is given in a module then it assumed to be:

  default (Integer, Double)

deriving

data and newtype declarations contain an optional deriving form. If the form is included, then derived instance declarations are automatically generated for the datatype in each of the named classes.

Derived instances provide convenient commonly-used operations for user-defined datatypes. For example, derived instances for datatypes in the class Eq define the operations == and /=, freeing the programmer from the need to define them.

data T = A
       | B
       | C
       deriving (Eq, Ord, Show)

In the case of newtypes, GHC extends this mechanism to Cunning Newtype Deriving.

deriving instance

Standalone deriving (GHC language extension).

{-# LANGUAGE StandaloneDeriving #-}
data A = A

deriving instance Show A

do

Syntactic sugar for use with monadic expressions. For example:

 do { x ; result <- y ; foo result }

is shorthand for:

 x >> 
 y >>= \result ->
 foo result

forall

This is a GHC/Hugs extension, and as such is not portable Haskell 98/2010. It is only a reserved word within types.

Type variables in a Haskell type expression are all assumed to be universally quantified; there is no explicit syntax for universal quantification, in standard Haskell 98/2010. For example, the type expression a -> a denotes the type forall a. a ->a. For clarity, however, we often write quantification explicitly when discussing the types of Haskell programs. When we write an explicitly quantified type, the scope of the forall extends as far to the right as possible; for example,

forall a. a -> a

means

forall a. (a -> a)

GHC introduces a forall keyword, allowing explicit quantification, for example, to encode existential types:

data Foo = forall a. MkFoo a (a -> Bool)
         | Nil

MkFoo :: forall a. a -> (a -> Bool) -> Foo
Nil   :: Foo

[MkFoo 3 even, MkFoo 'c' isUpper] :: [Foo]

foreign

A keyword for the Foreign Function Interface (commonly called the FFI) that introduces either a foreign import declaration, which makes a function from a non-Haskell library available in a Haskell program, or a foreign export declaration, which allows a function from a Haskell module to be called in non-Haskell contexts.

hiding

When importing modules, without introducing a name into scope, entities can be excluded by using the form

hiding (import1 , ... , importn )

which specifies that all entities exported by the named module should be imported except for those named in the list.

For example:

import Prelude hiding (lookup,filter,foldr,foldl,null,map)

if, then, else

A conditional expression has the form:

 if e1 then e2 else e3

and returns the value of e2 if the value of e1 is True, e3 if e1 is False, and _|_ otherwise.

 max a b = if a > b then a else b

import

Modules may reference other modules via explicit import declarations, each giving the name of a module to be imported and specifying its entities to be imported.

For example:

  module Main where
    import A
    import B
    main = A.f >> B.f

  module A where
    f = ...

  module B where
    f = ...

See also as, hiding , qualified and the page Import

infix, infixl, infixr

A fixity declaration gives the fixity and binding precedence of one or more operators. The integer in a fixity declaration must be in the range 0 to 9. A fixity declaration may appear anywhere that a type signature appears and, like a type signature, declares a property of a particular operator.

There are three kinds of fixity, non-, left- and right-associativity (infix, infixl, and infixr, respectively), and ten precedence levels, 0 to 9 inclusive (level 0 binds least tightly, and level 9 binds most tightly).

  module Bar where
    infixr 7 `op`
    op = ...

instance

An instance declaration declares that a type is an instance of a class and includes the definitions of the overloaded operations - called class methods - instantiated on the named type.

  instance Num Int  where
    x + y       =  addInt x y
    negate x    =  negateInt x

let, in

Let expressions have the general form:

let { d1 ; ... ; dn } in e

They introduce a nested, lexically-scoped, mutually-recursive list of declarations (let is often called let rec in other languages). The scope of the declarations is the expression e and the right hand side of the declarations.

Within do-blocks or list comprehensions let { d1 ; ... ; dn } without in serves to introduce local bindings.

mdo

The recursive do keyword enabled by -fglasgow-exts.

module

Taken from: A Gentle Introduction to Haskell, Version 98

Technically speaking, a module is really just one big declaration which begins with the keyword module; here's an example for a module whose name is Tree:

module Tree ( Tree(Leaf,Branch), fringe ) where

data Tree a                = Leaf a | Branch (Tree a) (Tree a) 

fringe :: Tree a -> [a]
fringe (Leaf x)            = [x]
fringe (Branch left right) = fringe left ++ fringe right

newtype

The newtype declaration is how one introduces a renaming for an algebraic data type into Haskell. This is different from type below, as a newtype requires a new constructor as well. As an example, when writing a compiler one sometimes further qualifies Identifiers to assist in type safety checks:

newtype SimpleIdentifier = SimpleIdentifier Identifier
newtype FunctionIdentifier = FunctionIdentifier Identifier

Most often, one supplies smart constructors and destructors for these to ease working with them.

See the page on types for more information, links and examples.

For the differences between newtype and data, see Newtype.

proc

proc (arrow abstraction) is a kind of lambda, except that it constructs an arrow instead of a function.

Arrow notation

qualified

Used to import a module, but not introduce a name into scope. For example, Data.Map exports lookup, which would clash with the Prelude version of lookup, to fix this:

import qualified Data.Map

f x = lookup x -- use the Prelude version
g x = Data.Map.lookup x -- use the Data.Map version

Of course, Data.Map is a bit of a mouthful, so qualified also allows the use of as.

import qualified Data.Map as M

f x = lookup x -- use Prelude version
g x = M.lookup x -- use Data.Map version

rec

The rec keyword can be used when the -XDoRec flag is given; it allows recursive bindings in a do-block.

{-# LANGUAGE DoRec #-}
justOnes = do { rec { xs <- Just (1:xs) }
              ; return (map negate xs) }

type

The type declaration is how one introduces an alias for an algebraic data type into Haskell. As an example, when writing a compiler one often creates an alias for identifiers:

type Identifier = String

This allows you to use Identifer wherever you had used String and if something is of type Identifier it may be used wherever a String is expected.

See the page on types for more information, links and examples.

Some common type declarations in the Prelude include:

type FilePath = String
type String = [Char]
type Rational = Ratio Integer
type ReadS a = String -> [(a,String)]
type ShowS = String -> String

type family

Declares a type synonym family (see type families). GHC language extension.

type instance

Declares a type synonym family instance (see type families). GHC language extension.


where

Used to introduce a module, instance, class or GADT:

module Main where

class Num a where
    ...

instance Num Int  where
    ...

data Something a where
   ...

And to bind local variables:

f x = y
    where y = x * 2

g z | z > 2 = y
    where y = x * 2