Convert a general collection of a specific type to a collection of a base type

I have several classes that implement a specific interface (ISearchable), and I would like to return an IEnumerable of the base type (ISearchable) from the static method, but I'm not sure how to convert it without intermediate collections.

The code is pretty simple, one of the implementations of domain objects is this:

public class account : ISearchable
{
    public static IEnumerable<ISearchable> Search(string keyword)
    {
        // ORMVendorCollection<T> implements IQueryable<T>
        ORMVendorCollection<account> results = /* linq query */

        // this works if I change the return type to IEnumerable<account>
        // but it uglifies client code a fair bit
        return results.AsEnumerable<account>();

        // this doesn't work, but it what I'd like to achieve            
        return results.AsEnumerable<ISearchable>(); 
    }
}

Client code, ideally, looks like this:

public static IEnumerable<ISearchable> Search(string keyword)
{
    return account.Search(keyword)
        .Concat<ISearchable>(order.Search(keyword))
        .Concat<ISearchable>(otherDomainClass.Search(keyword));
}
+3
source share
3 answers

Use extension method Cast<T>

return results.Cast<ISearchable>();
+7
source

For C # 4.0 you can use directly, since IEnumerable<> covariant

return (IEnumerable<ISearchable>)results.AsEnumerable();
+2
source

- ?

public class account : ISearchable 
{ 
    public static IEnumerable<ISearchable> Search(string keyword) 
    { 
        var results = /* linq query */ 
        foreach(var result in results)
            yield return result;
    } 
} 
+1

Source: https://habr.com/ru/post/1764199/


All Articles