I have rewritten some of my database accessing code, in order to save some cycles. My main goal was to achieve as much server-side evaluation of my LINQ querys as possible. In order to do so, i replaced this:
data = ...some LINQ...
if(condition){
data = data.Where(element => filter-condition)
}
with this:
data = ...some LINQ...
.Where(element => !condition || filter-condition)
condition
in this case is an expression that does not depend on the current element. So you could say it is practically a constant during the whole query, as it always evaluates to true for all elements in data
or it evaluates to false for all elements.
On the other hand filter-condition
is an expression that depends on the current element, as you would expect from you usual Where clause condition.
This optimization works like a charm, because it enables server-side evaluation in SQL on the database, and the LINQ to SQL compiler is intelligent enough to even short-cirquit the generated SQL if my condition
evaluates to false.
My question ist, what happens if this code is not evaluated in SQL on server-side. Lets say i would do the following:
data = ...some LINQ...
.AsEnumerable() //Enforces client-side query evaluation
.Where(element => !condition || filter-condition)
Now my Where clause gets evaluated client-side, which is not a problem on the functional side. Of course, the performance is weaker for client-side execution. But what about my custom optimization i did beforhand? Is there a performance penalty for evaluating condition
for every element in my data sequence? Or is LINQ on client-side also intelligent enough, to short-circuit the "constant" expression condition
?
Or is LINQ on client-side also intelligent enough, to short-circuit the "constant" expression condition?
Sort of. ||
always gets short-circuit evaluation in C#, but LINQ on the client does not have any sort of query optimizer, so the !condition || filter-condition
predicate will be evaluated for every entity.