Is there a way to handle any type of collection, instead of solely relying on Array, List, etc?

This example is for a method called "WriteLines", which takes an array of strings and adds them to an asynchronous file writer. It works, but I am curious if there is an interesting way to support -any- collection of strings, rather than relying on the programmer to convert to an array.

I came up with something like:

public void AddLines(IEnumerable<string> lines)
{
    // grab the queue
    lock (_queue)
    {
        // loop through the collection and enqueue each line
        for (int i = 0, count = lines.Count(); i < count; i++)
        {
            _queue.Enqueue(lines.ElementAt(i));
        }
    }
    // notify the thread it has work to do.
    _hasNewItems.Set();
}

This appears to work but I have no idea of any performance implications it has, or any logic implications either (What happens to the order? I assume this will allow even unordered collections to work, e.g. HashSet).

Is there a more accepted way to achieve this?

Jon Skeet
people
quotationmark

You've been passed an IEnumerable<string> - that means you can iterate over it. Heck, there's even a language feature specifically for it - foreach:

foreach (string line in lines)
{
    _queue.Enqueue(line);
}

Unlike your existing approach, this will only iterate over the sequence once. Your current code will behave differently based on the underlying implementation - in some cases Count() and ElementAt are optimized, but in some cases they aren't. You can see this really easily if you use an iterator block and log:

public IEnumerable<string> GetItems()
{
    Console.WriteLine("yielding a");
    yield return "a";
    Console.WriteLine("yielding b");
    yield return "b";
    Console.WriteLine("yielding c");
    yield return "c";
}

Try calling AddLines(GetItems()) with your current implementation, and look at the console...

people

See more on this question at Stackoverflow