You can implement your own method to make necessary expression tree, like here:
public static IQueryable<TEntity> WhereNotIn<TEntity, TValue>(
this IQueryable<TEntity> queryable,
Expression<Func<TEntity, TValue>> valueSelector,
IEnumerable<TValue> values)
where TEntity : class
{
if (queryable == null)
throw new ArgumentNullException("queryable");
if (valueSelector == null)
throw new ArgumentNullException("valueSelector");
if (values == null)
throw new ArgumentNullException("values");
if (!values.Any())
return queryable.Where(e => true);
var parameterExpression = valueSelector.Parameters.Single();
var equals = from value in values
select Expression.NotEqual(valueSelector.Body, Expression.Constant(value, typeof (TValue)));
var body = equals.Aggregate(Expression.And);
return queryable.Where(Expression.Lambda<Func<TEntity, bool>>(body, parameterExpression));
}
}
And now you can call this extension method
var badGuys = new int[] { 100, 200, 300 };
context.Persons.WhereNotIn(p => p.PersionId, badGuys);
This method makes the same thing as:
context.Persons.Where(p => p.PersonId != badGuys[0]
&& p.PersonId != badGuys[1]
. . .
&& p.PersonId != badGuys[N]);
for each element of badGuys
enumerable object.
An additional advantage of the method is its universality, cause you can call it for any property of any entity, f.e. context.Persons.WhereNotIn(p => p.LastName, new[] { "Smith", "Brown", "Jones" })
.