<div>I would like to propose the following function for inclusion in Data.List</div><div><br></div><div>chop :: (a -&gt; (b, [a]) -&gt; [a] -&gt; [b]</div><div>chop _ [] = []</div><div>chop f as = b : chop f as&#39;</div><div>
  where (b, as&#39;) = f as</div><div><br></div><div>It&#39;s commonly occuring recursion pattern.  Typically chop is called</div><div>with some function that will consume an initial prefix of the list</div><div>and produce a value and the rest of the list.</div>
<div><br></div><div>The function is clearly related to unfoldr, but I find it more</div><div>convenient to use in a lot of cases.</div><div><br></div><div>Some examples</div><div>-------------</div><div><br></div><div>-- From Data.List</div>
<div>group :: (Eq a) =&gt; [a] -&gt; [[a]]</div><div>group = chop (\ xs@(x:_) -&gt; span (==x) xs)</div><div><br></div><div>-- From Data.List</div><div>words :: String -&gt; [String]</div><div>words = filter (not . null) . chop (span (not . isSpace) . dropWhile isSpace)</div>
<div><br></div><div>-- From Data.List</div><div>lines :: String -&gt; [String]</div><div>lines = chop ((id *** dropNL) . span (/= &#39;\n&#39;))</div><div>  where dropNL (&#39;\n&#39;:s) = s; dropNL s = s</div><div><br></div>
<div>-- From Data.List</div><div>tails :: [a] -&gt; [[a]]</div><div>tails = (++ [[]]) . chop (\ xs@(_:xs&#39;) -&gt; (xs, xs&#39;))</div><div><br></div><div>-- From Data.List</div><div>map f = chop (\ (x:xs) -&gt; (f x, xs))</div>
<div><br></div><div>-- Split a list into a list of list with length n.</div><div>splitEveryN n = chop (splitAt n)</div><div><br></div><div>-- Simple Haskell tokenizer</div><div>tokenize = chop (head . lex)</div><div><br></div>
<div><br></div><div>History</div><div>-------</div><div><br></div><div>I first encountered this function around 1981 when I was talking to</div><div>Sören Holmström about this recursion pattern and he said that he</div><div>
had also observed it and he called the function chopList.</div><div>Ever since then I&#39;ve used chopList a lot, but unfortunately I always</div><div>have to make my own definition of this common function.</div><div><br>
</div>