Question

I have a function which returns a sequence of records. In that function I start the list building with a blank dummy record (there is probably a better way to do it) because I need to accumulate records that are similar, so I "prime the pump" with a blank record. Here's my code:

let consolidate(somethings:seq<Something>) =
    let mutable results = ResizeArray()
    let mutable accumulatedSomething = {Foo = ""; Bar = ""; Count = 0;}
    for s in somethings do
        if s.Foo = accumulatedSomething.Foo && s.Bar = accumulatedSomething.Bar then
           accumulatedSomething <- {Foo = s.Foo; Bar = s.Bar;
                                    Count = s.Count + accumulatedSomething.Count}
        else
            results.Add(accumulatedSomething)    
            accumulatedSomething <- e
    results |> Seq.cast |> Seq.skip 1

If you have a way to make this better I'm all ears (I'm still thinking procedurally) but I'm still interested in an answer to this specific question. Later on in my code, I try to print out the list:

somethings |> Seq.iter( fun s -> printfn "%A" s)

This works fine when there is stuff in the list. But if the list is empty and the only record that was in the list was the skipped blank starter record, then this line fails with an InvalidOperationException with the message The input sequence has an insufficient number of elements?

Why does this happen and how can I fix it?

Was it helpful?

Solution

The problem occurs when somethings is an empty list.

In this case, results is empty and calling Seq.skip 1 on the empty list fails with an error.

I think an elegant solution would be to change the last line to

match results.Length with
| 0 -> results |> Seq.cast
| _ -> results |> Seq.cast |> Seq.skip 1
Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top