Преобразование универсальной коллекции конкретного типа в коллекцию базового типа - PullRequest
3 голосов
/ 10 сентября 2010

У меня есть несколько классов, которые реализуют определенный интерфейс ( ISearchable ), и я хотел бы вернуть IEnumerable базового типа ( ISearchable ) из статическогометод, но я не уверен, как преобразовать его без создания промежуточных коллекций.

Код довольно прост, одна из реализаций объектов домена выглядит так:

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's what I'd like to achieve            
        return results.AsEnumerable<ISearchable>(); 
    }
}

код клиента, в идеале выглядит так:

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

Ответы [ 3 ]

7 голосов
/ 10 сентября 2010

Используйте метод расширения Cast<T>

return results.Cast<ISearchable>();
2 голосов
/ 10 сентября 2010

Для C # 4.0 вы можете иметь возможность разыгрывать напрямую, поскольку IEnumerable<> является ковариантным

return (IEnumerable<ISearchable>)results.AsEnumerable();
1 голос
/ 10 сентября 2010

Не могли бы вы просто сделать что-то вроде?

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