HOOG `M \M ! - : < > @ _ a c d e # f g h ! ! # # i k l m n ! ! o p " " q r # # s t ! " u v w # # x y " " |$ $ ~% % { s k i a Y ] e o w % { e Q 7 u _ G / u a M 7 ) ~! ~% |/ |$ whereA where# typeV type" thenj then! qualified qualified of of newtype newtype module module mdo mdo let let keyword keyword instance instance infixr: infixr infixlR infixl infixi infix in| in import import if if hiding hiding foreign foreign forall forall else else do do deriving( deriving defaultC default dataZ data classo class case case as as _ _ @ @ > > <- <- :: :: -> -> -- -- ! ! % I H \G F E E C B A : 9 h7 5 3 2 1 - C- + * ) 5' $ c" a * = ' ~ keyword ~ 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.
(f *** g) ~(x,y) = (f x, g y)| keyword | & The "pipe" is used in several places Data type definitions, "or"
data Maybe a = Just a | NothingList comprehensions, "where"
squares = [a*a | a <- [1..]]Guards, do this "if this is true"
safeTail x | null x = [] | otherwise = tail xwhere keyword where Used to introduce a module, instance or class:
module Main where class Num a where ... instance Num Int where ...And to bind local variables:
f x = y where y = x * 2 g z | z > 2 = y where y = x * 2type keyword type9 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 = StringThis 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 -> Stringthen keyword then A conditional expression has the form:
if e1 then e2 else e3and 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 bqualified keyword 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 versionOf 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 versionof keyword ofF A case expression has the general form
case e of { p1 match1; ...; pn matchn }where each match is of the general form
| g1 -> e1 ... | gm -> em where declsEach alternative consists of a pattern pi and its matches, matchi. Each match in turn consists of a sequence of pairs of guards gj and bodies ej (expressions), followed by optional bindings (decls) that scope over all of the guards and expressions of the alternative. An alternative of the form
pat -> exp where declsis treated as shorthand for:
pat | True -> exp where declsA 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 _|_. newtype keyword newtypef 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 IdentifierMost 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. module keyword moduleQ taken from: http://www.haskell.org/tutorial/modules.html 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 rightmdo keyword mdo? <