F# split sequence into sub lists on every nth element

后端 未结 8 865
时光说笑
时光说笑 2020-12-06 11:23

Say I have a sequence of 100 elements. Every 10th element I want a new list of the previous 10 elements. In this case I will end up with a list of 10 sublists.

Seq.t

8条回答
  •  执念已碎
    2020-12-06 11:57

    I think that the solution from Brian is probably the most reasonable simple option. A probelm with sequences is that they cannot be easily processed with the usual pattern matching (like functional lists). One option to avoid that would be to use LazyList from F# PowerPack.

    Another option is to define a computation builder for working with IEnumerator type. I wrote something like that recently - you can get it here. Then you can write something like:

    let splitEach chunkSize (s:seq<_>) =
      Enumerator.toSeq (fun () -> 
        let en = s.GetEnumerator()
        let rec loop n acc = iter {
          let! item = en
          match item with 
          | Some(item) when n = 1 -> 
              yield item::acc |> List.rev 
              yield! loop chunkSize []
          | Some(item) -> 
              yield! loop (n - 1) (item::acc)
          | None -> yield acc |> List.rev }
        loop chunkSize [] )
    

    This enables using some functional patterns for list processing - most notably, you can write this as a usual recursive function (similar to the one you would write for lists/lazy lists), but it is imperative under the cover (the let! constructo of iter takes the next element and modifies the enumerator).

提交回复
热议问题