ScottishTapWater
ScottishTapWater

Reputation: 4776

Return same Type as Generic Class

Wasn't really sure how to phrase the title.

What I am trying to achieve is a deep clone system for IEnumerable<T>s where T:ICloneable.

I have written the, as-yet untested, method below which I believe should work:

    public static IEnumerable<T> DeepClone<T>(this IEnumerable<T> source) where T:ICloneable
    {
        return source.Select(s => (T) s.Clone());
    }

However, this returns an IEnumerable<T> (as one would expect) and I am curious as to whether or not it is possible (without causing an unacceptable overhead) to return the base type of the IEnumerable<T> instead.

For example, running List<int>.DeepClone() would return a new, cloned List<int> and running int[].DeepClone() would return a new, cloned int[].

I know that I can quite easily just cast my IEnumerables after calling this method, but I'm hoping to be able to avoid this.

There is also the option of creating a whole load of overloads, one for each IEnumerable but if it's possible to I'd like to avoid this.

Upvotes: 0

Views: 96

Answers (1)

mjwills
mjwills

Reputation: 23820

You will need to build explicit methods for the concrete types you want to support (List, arrays etc).

An example:

public static List<T> DeepClone<T>(this List<T> source) where T : ICloneable
{
    return source.Select(s => (T)s.Clone()).ToList();
}

Alternatively, use an approach like:

public static IEnumerable<T> DeepClone<T>(this IEnumerable<T> source) where T : ICloneable
{
    var result = source.Select(s => (T)s.Clone());

    if (source is List<T>)
    {
        return result.ToList();
    }

    return result;
}

Upvotes: 1

Related Questions