Alex Rivera | Logout

Is it a mistake to return a list if the return type is an enumerable

Asked 2010-07-16T10:19:30.990
13

I have often the case where I want to return an Enumerable<T> from a method or a property. To build the returning Enumerable<T>, I use a List<T>-instance. After filling the list, I return the list.

I always thought that this is enough. But it exists the possibility that the caller casts the resulting Enumerable<T> back into the List<T> and begins to work further with it. If in a later time I change the implementation of my method, the caller’s code will fail. To avoid this, I could return list.ToArray or make a read-only list before returning it to the caller. But for me this seems to be a big overkill. What do you think?

Please note, I never will return an internally used list so that the caller can change my objects internal state. The question is only about a short living list that is built temporary to hold the return values.

IEnumerable<string> GetAList() {
    List<string> aList = new List<string>();
    aList.Add("a");
    aList.Add("b");
    return aList;
}

IEnumerable<string> GetAList() {
    List<string> aList = new List<string>();
    aList.Add("a");
    aList.Add("b");
    return aList.ToArray<string>();
}

The examples are super-simple and in this case I would work from the beginning on with arrays, but it’s only to show explain the question.

c#
Edit
Report

3 Answers

4

Thought I'd make this a full fledged answer instead of just a comment.

AS others have said if you obey the contract an return an ienumerable others shouldn't make any more assumptions than that. However, some people might. If you then change it they are inevitably goign to come and blame you for it breaking (if they didn't understand enough to code it properly in the first place they are unlikely to spot the bug quickly).

When this happens you have two possibilities. You tell them its their problem and then leave them to fix it or you change your code to support theirs. The correct solution is the first one. However, in business this might not be feasible. If its a client that your bosses say you need to keep happy you might be told your code needs to change to keep the client happy and keep his business.

So from this point of view although it isn't your responsibility it can become your problem.

If your code is easily refactorable to return the exact type promised then I would do that. Its potentially little work now to save lots of work later and in theory nobody should even notice your change.

answered 2010-07-16T10:36:09.403
3

I think that your problem is farfetched because if someone improperly using your methods (making assumption about internal implementation), then actually that is not your problem.

But you if you using .net 3.5, then you can use AsEnumerable to completely hide internal implementation:

return aList.AsEnumerable();

Or simply wrap list with yield

foreach (string NextStr in aList)
    yield return NextStr;
answered 2010-07-16T10:25:55.560
1

If you change your implementation later on, and return something other than a List<T>, the caller code will indeed break. But the author of the caller code should know better than just casting to List<T> without checking that the return value actually is a list - you have promised nothing of the sort.

As for myself, I tend to return theList.AsEnumerable(), just to be extra clear, but that is not necessary. The caller code will not know anything about what implementation of *IEnumerable<T> is returned - just that some implementation is returned.

answered 2010-07-16T10:26:40.567

Your Answer