Question

I am new to functional programming and learning Haskell. I have a list of indices and a list of elements that I want to split according to the list of indices (sorted in increasing order).

splitByIndices :: [a] -> [Int] -> [[a]]

I am thinking of take indexlist[n] and drop indexlist[n-1] but do not know how to implement it with foldl. Please help! Thanks!

Example:

splitByIndices [1,2,3,4,5] [1,2] = [1],[2],[3,4,5]
Was it helpful?

Solution 2

splitByIndices :: [a] -> [Int] -> [[a]]
splitByIndices xs is = go xs (zipWith subtract (0:is) is) where
    go [] _      = []
    go xs (i:is) = let (a, b) = splitAt i xs in a : go b is
    go xs _      = [xs]

This of course produces incorrect results when the indices aren't strictly increasing. You could enforce this condition with:

import Data.List

enforce :: [Int] -> [Int]
enforce = map head . group . sort

and then you can use enforce is instead of is.

OTHER TIPS

The split package offers this by the name splitPlaces.

I have solved this with foldr, it is kind of complicated:

splitByIndices :: [String] -> [Int] -> [[String]]
splitByIndices input indexlist = foldr (\elem acc -> [fst $ splitAt elem $ head acc] ++ [snd $ splitAt elem $ head acc] ++ (tail acc)) [input] indexlist
Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top