Proposal: Add functions to get consecutive elements to Data.List

Andreas Abel abela at chalmers.se
Wed Apr 13 06:37:16 UTC 2016


I am neutral on this proposal.  I grepped the Agda source (100kloc) for 
zip.*tail and get 6 uses that fall into your pattern.
However, I am not so sure this warrants a new function, in the end

   zipConsecutivesWith f xs

is not shorter than

   zipWith f xs (tail xs)

unless xs is a long name.

./TypeChecking/Free/Tests.hs:54:strictlyAscending l = and $ zipWith (<) 
l $ tail l
./TypeChecking/Errors.hs:709:          two = zipWith (\a b -> [a,b]) s 
(tail s)
./Interaction/Highlighting/Precise.hs:225:  and (zipWith (<=) (map to $ 
init rs) (map from $ tail rs))
./Interaction/Highlighting/Range.hs:52:  and (zipWith (<) (map to $ init 
rs) (map from $ tail rs))
./Syntax/Position.hs:169:  and (zipWith (<) (map iEnd $ init is) (map 
iStart $ tail is))
./Utils/List.hs:219:sorted xs = and $ zipWith (<=) xs (tail xs)

On 12.04.2016 22:55, Johan Holmquist wrote:
> I propose adding two new functions to Data.List:
>
>      zipConsecutives :: [a] -> [(a,a)]
>      zipConsecutives xs = zip xs (tail xs)
>
>      zipConsecutivesWith :: (a -> a -> b) -> [a] -> [b]
>      zipConsecutivesWith f xs = zipWith f xs (tail xs)
>
> (with possibly more efficient implementations)
>
> The Trac feature request is at
> https://ghc.haskell.org/trac/ghc/ticket/11815.
>
>
> Why
>
> These functions are useful when one wants to process consecutive pairs
> of elements in a sequence, which is not uncommon. The ticket lists
> some examples, reiterated here:
>
>      -- diff consecutive elements:
>      diffs = zipConsecutivesWith (flip (-))
>
>      -- determine if list is ascending (similar for descending and strict):
>      isAscending = and . zipConsecutivesWith (<=)
>
>      -- an old friend of ours:
>      fibs = 1 : 1 : zipConsecutivesWith (+) fibs
>
>      -- get the edges of a closed path defined by points (ps):
>      edges ps = zipConsecutivesWith makeEdge (ps ++ take 1 ps)
>
>
> Why add to Data.List (and base)
>
> The definition must either use an extra equation for the empty list case:
>
>      zipConsecutives [] = []
>      zipConsecutives xs = zip xs (tail xs)
>
> which makes it non practical to define inline at each use site. Or one
> may omit the empty list equation, which is safe (thanks to laziness),
> but that may not be immediately obvious. (It wasn't to me anyway.) The
> tail function is generally considered unsafe so it is not desirable to
> force the user to use it. The proposed functions would offer an
> alternative.
>
>
> The Data.List module is often imported unqualified, so new identifiers
> may cause collissions. I do find it rather unlikely that the proposed
> names would cause such problems, however.
>
>
> Deadline for discussion: 2016-05-31.
>
>
> _______________________________________________
> Libraries mailing list
> Libraries at haskell.org
> http://mail.haskell.org/cgi-bin/mailman/listinfo/libraries
>


-- 
Andreas Abel  <><      Du bist der geliebte Mensch.

Department of Computer Science and Engineering
Chalmers and Gothenburg University, Sweden

andreas.abel at gu.se
http://www2.tcs.ifi.lmu.de/~abel/


More information about the Libraries mailing list