Entity Framework 4 - Die Eigenschaft Contains unterstützt Arrays
Was in Linq to SQL kein Problem darstellte, ist im Entity Framework 1 eine kleine Herausforderung. Allein deswegen habe ich mich mit Entity SQL (eSQL) auseinandergesetzt.
Der Ablauf war sehr einfach. Bei der Abfrage konnte man nach dem Inhalt eines Arrays suchen lassen und bekam das Resultat von der Datenquelle zurück. Der Code dafür ist leicht verständlich.
C#
int[] valueArray = new int[] { 3, 4, 5, 9 };
var result = from d in context.Dispatchings
where valueArray.Contains(d.diAutoID)
select d;
Neben eSQL gibt es für das Entity Framework einen Workaround, der ein schreckliches OR-Konstrukt an die Datenquelle sendet und auch noch so heisst: BuildOrExpression.
C# (Workaround BuldOrExpression)
public static Expression<Func<TElement, bool>> BuildOrExpression<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();
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(
(accumulate, equal) => Expression.Or(accumulate, equal)
);
return Expression.Lambda<Func<TElement, bool>>(body, p);
}
Im Code konnte dieser Ausdruck nur in Lamda-Ausdrücken verwendet werden. In der Linq-Syntax habe ich diesen Workaround nie zum laufen gebracht.
C# (Einsatz BuildOrExpression)
int[] valueArray = new int[] { 3, 4, 5, 9 };
var result = context.Dispatchings.Where(
EfExtensions.BuildOrExpression<Dispatching,int>
(v => v.diAutoID, valueArray)
);
Im Entity Framework 4 sind diese Spielereien nicht mehr notwendig. Die Array-Unterstützung der Eigenschaft IEnumerable.Contains trägt auch dazu bei, dass der Code verständlicher wird.
C# (Abfrage in EF4)
var result = from d in context.Dispatchings
where valueArray.Contains(d.diAutoID)
select d;
Ehrlich, der Code sieht doch viel besser aus, wenn man die Eigenschaftsnamen aussen vor lässt.
Good bye BuildOrExpression!
- 0 Kommentar(e)



Mein Kommentar