|
Replies:
4
-
Pages:
1
-
Last Post:
Feb 9, 2009 11:13 AM
by: fabrice.marguerie
|
|
|
Posts:
2
From:
England
Registered:
2/5/09
|
|
|
|
Can anyone convert this query expression into a query operator chain?
Posted:
Feb 5, 2009 5:58 PM
|
|
Hi all,
For the past couple of days I've been reading the excellent 'LINQ in Action'. During its coverage of 'LINQ to Objects' the book uses the following query expression to perform a left outer join:
***
from publisher in SampleData.Publishers join book in SampleData.Books on publisher equals book.Publisher into publisherBooks from book in publisherBooks.DefaultIfEmpty() select new { Publisher = publisher.Name, Book = book == default(Book) ? "(no books)" : book.Title };
***
Basically, I'm hoping that some clever reader will be able to tell me how this query can be represented using pure query operator calls. If so, I'd be eternally grateful for their response as I'm truly at my wits end!
Many thanks indeed!
James
|
|
Posts:
209
From:
France
Registered:
4/28/06
|
|
|
|
Re: Can anyone convert this query expression into a query operator chain?
Posted:
Feb 5, 2009 7:23 PM
in response to:
JamesEdCraig
|
|
Hi James,
I'm not surprised that you haven't found how to write this query without the query expression syntax! It's not easy to do the conversion because it requires the use of tricks. Here the tricks are based on the use of anonymous types.
Here is the solution:
SampleData.Publishers .GroupJoin(SampleData.Books, publisher => publisher, book => book.Publisher, (publisher, publisherBooks) => new { Publisher = publisher, PublisherBooks = publisherBooks }) .SelectMany( group => group.PublisherBooks.DefaultIfEmpty<Book>(), (group, book) => new { Publisher = group.Publisher.Name, Book = (book == null) ? "(no books)" : book.Title }); Not as easy to read as your original query, don't you think?
"How did he find that," you may be wondering... Well, even if I know the tricks, the easiest is to use .NET Reflector to decompile the IL. If you specify ".NET 3.5" for the Optimization option, you'll see the query expression. But if you specify ".NET 2.0", you'll see something that looks close to the above query. You'll have to replace the anonymous methods with lambda expressions and change the name of the anonymous parameters to make the code somewhat more readable, though.
As usual, Reflector reveals a lot of secrets 
Fabrice
|
|
Posts:
2
From:
England
Registered:
2/5/09
|
|
|
|
Re: Can anyone convert this query expression into a query operator chain?
Posted:
Feb 6, 2009 6:48 AM
in response to:
fabrice.marguerie
|
|
Hi Fabrice,
Many thanks for taking the time to write this solution, and also for suggesting that neat Reflector trick! I'll most definitely be making good use of both in the future 
Finally, I have to congratulate you on your book. I began reading it a couple of days ago and have enjoyed immensely its lucid, comprehensive exploration of LINQ. The fact that the boss has granted me time to read it has made learning the subject more enjoyable still!
merci beaucoup!
James
|
|
Posts:
209
From:
France
Registered:
4/28/06
|
|
|
|
Re: Can anyone convert this query expression into a query operator chain?
Posted:
Feb 6, 2009 6:59 AM
in response to:
JamesEdCraig
|
|
You're welcome. Thanks for sharing your impression. I'm glad that you're enjoying our book!
|
|
Posts:
209
From:
France
Registered:
4/28/06
|
|
|
|
Re: Can anyone convert this query expression into a query operator chain?
Posted:
Feb 9, 2009 11:13 AM
in response to:
fabrice.marguerie
|
|
Additional tips left as comments to the post on my blog: - You can call ToString() on the Expression in the IQueryable created (if the query is of the IQueryable type) - ReSharper has a convert to method chain option
|
|
|
Legend
|
|
Gold: 300
+
pts
|
|
Silver: 100
- 299
pts
|
|
Bronze: 25
- 99
pts
|
|
Manning Author
|
|
Manning Staff
|
|