2

How would you implement take with a list comprehension?

My approach so far:

take2 :: (Num i, Ord i) => i -> [a] -> [a]
take2 n xs = [x | x <- xs, [x..n]]
Lii
  • 11,553
  • 8
  • 64
  • 88
Michi
  • 41
  • 7

4 Answers4

8

The fundamental reason why list comprehensions are not a good fit for the take function is this:

The take function stops the evaluation of the argument list after n elements.

But lists comprehensions always evaluate all elements of the list in the generator. There is no break-statement in Haskell.


You can use some trick to truncate the list before or after using it in the list comprehension, but there is no real point of doing so. That would be similar to first using normal take to truncate the list, then using a list comprehension just to return the result.

Lii
  • 11,553
  • 8
  • 64
  • 88
7

We can use a zip approach here, and enumerate over both the elements, and indices, like:

take2 :: (Num i, Enum i) => i -> [a] -> [a]
take2 n xs = [x | (x, _) <- zip xs [1..n]]

Or with the ParallelListComp extension:

{-# LANGUAGE ParallelListComp #-}

take2 :: (Num i, Enum i) => i -> [a] -> [a]
take2 n xs = [x | x <- xs | _ <- [1..n]]

But actually take is probably not a function that is a good fit for list comprehension in the first place.

Willem Van Onsem
  • 443,496
  • 30
  • 428
  • 555
0

Without List Comprehension

take' :: Int -> [Int] -> [Int]
take' _ [] = []
take' _ [x] = [x]
take' n all@(x : xs)
        | (n > length all) = error "Index too large"
        | (n == length all) = all
        | (n == 0) = []
        | (n < length all) =  x : [] ++ (take' (n-1) xs)
Damilare
  • 1
  • 5
0
take' :: Int -> [a] -> [a]
take' n xs = [xs !! i | i <- [0..n-1]]
  • 1
    Code-only answers are considered low quality: make sure to provide an explanation what your code does and how it solves the problem. It will help the asker and future readers both if you can add more information in your post. See also Explaining entirely code-based answers: https://meta.stackexchange.com/questions/114762/explaining-entirely-code-based-answers – borchvm Jan 31 '20 at 06:59