Prev Up Next
Go backward to Evaluation Strategies
Go up to Strategies Separate Algorithm from Dynamic Behaviour
Go forward to Combining Strategies

Strategies Controlling Evaluation Degree

The simplest strategies introduce no parallelism: they specify only the evaluation degree. The simplest strategy is termed r0 and performs no reduction at all. Perhaps surprisingly, this strategy proves very useful, e.g. when evaluating a pair we may want to evaluate only the first element but not the second.
r0 :: Strategy a 
r0 _ = ()
Because reduction to WHNF is the default evaluation degree in GpH, a strategy to reduce a value of any type to WHNF is easily defined:
rwhnf :: Strategy a 
rwhnf x = x `seq` ()

Many expressions can also be reduced to normal form (NF), i.e. a form that contains no redexes, by the rnf strategy. The rnf strategy can be defined over built-in or datatypes, but not over function types or any type incorporating a function type as few reduction engines support the reduction of inner redexes within functions. Rather than defining a new rnfX strategy for each data type X, it is better to have a single overloaded rnf strategy that works on any data type. The obvious solution is to use a Haskell type class, NFData, to overload the rnf operation. Because NF and WHNF coincide for built-in types such as integers and booleans, the default method for rnf is rwhnf.

class NFData a where
  rnf :: Strategy a
  rnf = rwhnf

For each data type an instance of NFData must be declared that specifies how to reduce a value of that type to normal form. Such an instance relies on its element types, if any, being in class NFData. Consider lists and pairs for example.

instance NFData a => NFData [a] where
  rnf [] = ()
  rnf (x:xs) = rnf x `seq` rnf xs

instance (NFData a, NFData b) => NFData (a,b) where
  rnf (x,y) = rnf x `seq` rnf y 


Prev Up Next