To get around this limitation, you can manually create an expression (Source)
FROM#
static Expression<Func<TElement, bool>> BuildContainsExpression<TElement, TValue>( Expression<Func<TElement, TValue>> valueSelector, IEnumerable<TValue> values) { if (null == valueSelector) { throw new ArgumentNullException("valueSelector"); } if (null == values) { throw new ArgumentNullException("values"); } ParameterExpression p = valueSelector.Parameters.Single(); // p => valueSelector(p) == values[0] || valueSelector(p) == ... if (!values.Any()) { return e => false; } var equals = values.Select(value => (Expression)Expression.Equal(valueSelector.Body, Expression.Constant(value, typeof(TValue)))); var body = equals.Aggregate<Expression>((accumulate, equal) => Expression.Or(accumulate, equal)); return Expression.Lambda<Func<TElement, bool>>(body, p); }
Using this utility method,
var query2 = context.Entities.Where(BuildContainsExpression<Entity, int>(e => e.ID, ids));
Vb.net
Public Shared Function BuildContainsExpression(Of TElement, TValue)( _ ByVal valueSelector As Expression(Of Func(Of TElement, TValue)), _ ByVal values As IEnumerable(Of TValue) _ ) As Expression(Of Func(Of TElement, Boolean)) ' validate arguments If IsNothing(valueSelector) Then Throw New ArgumentNullException("valueSelector") If IsNothing(values) Then Throw New ArgumentNullException("values") Dim p As ParameterExpression = valueSelector.Parameters.Single() If Not values.Any Then Return _ Function(e) False End If Dim equals = values.Select( _ Function(v) _ Expression.Equal(valueSelector.Body, Expression.Constant(v, GetType(TValue))) _ ) Dim body = equals.Aggregate( _ Function(accumulate, equal) _ Expression.Or(accumulate, equal) _ ) Return Expression.Lambda(Of Func(Of TElement, Boolean))(body, p) End Function
Using this utility method
Dim query = m_data. Offer If (selectedSectors.Count > 0) Then query = query.Where(BuildContainsExpression(Function(o As Offer) o.Value, selectedSectors)) End If
Alexandre Brisebois
source share