Прежде всего, вы не можете создать новую IQueryable из массива это будет вернуться к вытягивать все в памяти и фильтрации там. Вы работаете с выражениями, а не с кодом C# при LINQ с SQL, это будет работать только в памяти (IEnumerable). Ваш запрос будет работать в SQL, если вы делаете это как этот
from element in MyPredicateContext
where ids.Contains(element.Id)
select new Element
{
Id = element.Id,
Description = element.JobDescription,
}
Учитывая, что тип IQueryable где T представляет собой интерфейс или класс. Метод конечных будет выглядеть как этот
public interface IElement
{
Guid Id { get; }
string JobDescription { get; }
}
public Element[] GetByIds<T>(IQueryable<T> myPredicateContext, Guid[] ids) where T:IElement
{
return (from element in myPredicateContext
where ids.Contains(element.Id)
select new Element
{
Id = element.Id,
Description = element.JobDescription,
}).ToArray();
}
Есть способы сделать это без каких-либо дженериков, но они немного более продвинутый и будет трудно поддерживать.
Вот метод, который будет работать на всех типах T, и правильный IQueryable будет производить хороший sql, как я уже указывал, немного более продвинутый, и вам нужно будет найти, как работает выражение.
public static Element[] GetById<T, Tkey>(IQueryable<T> items,Tkey[] ids)
{
var type = typeof(T);
ParameterExpression param = Expression.Parameter(type);
var list = Expression.Constant(ids);
//The names of the properties you need to get if all models have them and are named the same and are the same type this will work
var idProp = Expression.Property(param, "Id");
var descriptionProp = Expression.Property(param, "JobDescription");
var contains = typeof(Enumerable).GetMethods().First(m => m.Name == "Contains" && m.GetParameters().Count() == 2).MakeGenericMethod(typeof(Tkey));
var where = Expression.Lambda<Func<T, bool>>(Expression.Call(contains, list, idProp), param);
return (items.
Where(where).
Select(Expression.Lambda<Func<T, Element>>(
Expression.MemberInit(
Expression.New(typeof(Element)),
Expression.Bind(typeof(Element).GetProperty("Id"), idProp),
Expression.Bind(typeof(Element).GetProperty("Description"), descriptionProp)),
param))).ToArray();
}
Вызов GetById(items, new Guid[] { Guid.NewGuid() })
Почему вы хотите контекст в качестве параметра, а не таблицы? Или вы хотите оба? И я думаю, что все ваши элементы не имеют свойства JobDescription, не так ли? –