map* for Data.List

Henning Thielemann lemming at henning-thielemann.de
Mon Nov 6 06:06:56 EST 2006


On Sat, 4 Nov 2006, Bulat Ziganshin wrote:

> Hello libraries,
> 
> similar to mapFst and Co, we can define:
> 
> -- |Map various parts of list
> mapHead f []      =  []
> mapHead f (x:xs)  =  f x : xs
> 
> mapTail f []      =  []
> mapTail f (x:xs)  =  x : map f xs
> 
> mapInit f []      =  []
> mapInit f xs      =  map f (init xs) : last xs
> 
> mapLast f []      =  []
> mapLast f xs      =  init xs : map f (last xs)
> 
> 
> btw, two last operations may be a bit slow. it's possible to define
> initLast function that returns both parts and still lazy?

In order to make such operations more efficient I defined:

{- | It holds @splitLast xs == (init xs, last xs)@,
     but 'splitLast' is more efficient
     if the last element is accessed after the initial ones,
     because it avoids memoizing list.
-}
splitLast :: [a] -> ([a], a)
splitLast [] = error "splitLast: empty list"
splitLast [x] = ([], x)
splitLast (x:xs) =
   let (xs', lastx) = splitLast xs in (x:xs', lastx)

propSplitLast :: Eq a => [a] -> Bool
propSplitLast xs =
   splitLast xs  ==  (init xs, last xs)


More information about the Libraries mailing list