Consider the following definition taken from a tutorial at http://www.haskell.org :
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
I am unclear about what happens at runtime when the function fringe is executing.
When compiling the expression fringe left , 
(1) does the compiler somehow already know if the left tree is a Branch or
a Leaf - i.e. it only operates on statically known trees - or (2) does it emit some if/switch like conditions to check if the left tree is a Leaf or a Branch
If it is the later i.e. (2), then, why is this supposed to be more typesafe than the equivalent C function which basically would look just like above except that there is only one type floating around (pointer to a node).