Hi Stefan -

Your crucial statement seems to be:

> Now I want to write the following query:
> 
> SELECT ... FROM ... WHERE A = B

That outs you as a "Let's-SQLer", in my nomenclature ;-). For us (few) "Linq 
purists", this is the same statement as the one we had in the '80s:

"Now I want to place that integer variable into a register".

(That was the reason that C originally had a "register" - and "auto" - 
keyword). And even your sentiments were shared at that time, too:
* It should be obvious to everyone that assembler code must be readable!
* It should be obvious to everyone that the generated code must run with high 
performance!

The first statement became irrelevant with the introduction of source 
code-level debuggers. I must concede: There will be no parallel here - we will 
live with tools on SQL level forever.
It also became irrelevant when the generated assembler was optimized in ways 
that made unreadable because of its tricky structure (no longer 1:1 to source 
code).
The second statement is never irrelevant - also not for our SQL debate.

So, it seems that my comparison is not really valid, and you are "right" ... 
Anyway, I justed want to point out that we already had similar discussions; and 
they did not go in the direction of the "pure metal".

Still, I'd like to argue for "pure Linq" as follows:

(a) Do you really want to *write* (your term!) that query? I would believe that 
you want to retrieve objects from the database that fulfil a condition, with 
good performance. Why do you care what the WHERE part of the query looks like?

Ah ... we all know: that SQL text is a good indicator of performance; and 
because you don't believe your database full-heartedly, you want to play around 
with the statement (check the plan, have it run on different data etc.), and 
hence is must be readable - e.g. in a profiler. Yes - unfortunately these are 
valid concerns. Still, they are valid only for a minority of the queries in a 
program - where you'll have to optimize in many ways; putting the burden solely 
on the translation = operator will not work in most cases, anyway, or would it?

(b) Do you really need that SQL = *semantics*? I.e., do you *want* to *not* get 
the objects where both A and B are null? In all my career, I have not seen 
application code that *relied* on such a result (except that sort of "clever 
code" that needs more lines of comment to explain it than a plausible code that 
distinguishes cases). Still, there is an argument there ...

(c) If you really want to "write" exactly that query, then write it - in SQL!

(d) Ok - you want to use a good OR mapper. Then write it in HQL. HQL has been 
with us for (I think more than) 10 years and has been used productively in huge 
systems (like ours - 5 millions LOCs, 25 developers over 5 years, 1000s of 
queries, some very complex etc.etc.). Why would you want to "hijack" Linq for 
this?

(e) You want Linq (for whatever reasons). What is wrong with (A = B OR A IS 
NULL AND B IS NULL)? It is reasonably easy to read, it is correct, it is 
performant - at least on SQL Server (yes: I do not know what happens on other 
databases), it uses the indices as you expect - no table scans (we transform 
our pre-Linq expression language to it - so we know it; having used SQL server 
2000, 2005, 2008).

(f) What is wrong with NHibernate optimizing away the IS NULL parts *if* the 
property type (e.g. int) or the mapping file tells it that the property is not 
nullable (the second would be akin to the "register" keyword mentioned above)?

(g) Actually, I expect the database to optimize away that expressions if they 
are never true. Because of many "useless" expressions that are the result of 
"SQL generators" (many programs create their SQL programmatically), databases 
are getting better and better at this.

... that's all I currently can think of ...

I just wanted to put down these arguments so that it hopefully clear what a 
"Linq purist"'s standpoint could be. I do *not* say that this is "the only way 
to go", that this "must be how NHibernate behaves". What I do say is that it is 
often (too?) implicit in my (and others?) arguments, and it might help you all 
to understand sometimes what I say or even implement.

Obviously, I very much like your remark

> An alternative query factory method would probably be a good place to put it.

And I would definitely not have a problem if the "purist factory" would *not* 
be the default. (And yes, also that "purist factory" would not be *that* purist 
- see that trailing blank example I gave in another posting. Performance on the 
database is important. There's no way around this ...). Maybe I'll try to find 
out how I could add this to NHibernate - either by convincing you (the NHib 
team) to do this; or by pulling it off outside NHib - as I already did with our 
current "OurExpressions to HQL" generator.

Best regards
Harald

-- 
GMX DSL Doppel-Flat ab 19,99 Euro/mtl.! Jetzt mit 
gratis Handy-Flat! http://portal.gmx.net/de/go/dsl

Reply via email to