Nested query in entity framework

I had this error too. I had code like this:

var Games = context.Games.Select(a => new GameModel
{
    Members = (!filters.GetDatailedDataToo ? null : new List<MemberModel>())
};

This error occurs when null is used in ? : operation.

This is not that case, written up here, but I've wasted lot of time, I think anyone uses this case, who searches this error text..


You're overestimating the power of LINQ translation to SQL. Not everything is translatable and there is no compiler warning for that due to the way LINQ works.

Nested collections are usually either a) not supported or b) end up in horrible SELECT N+1 queries. What you ask EF to do is to return an object tree. SQL does not support tree like results so you run into the object-relational impedance mismatch and it hurts.

I advise you to fetch the nested collection data as a second, completely separate query. That allows you more control and is guaranteed to work.

As a non-essential side-note, you will probably not be able to convince EF to use the ?: operator over sequences. That is very hard to translate. Think how you would write this as SQL - very hard and convoluted.


It looks like Linq to EF doesn't support the following

context.Games.Select(g => new
{
    Field = g.IsX? queryable1 : queryable2
});

But, here's a hack you can use to get it to work:

context.Games.Select(g => new
{
    Field = queryable1.Where(q => g.IsX)
               .Concat(queryable2.Where(q => !g.IsX))
});

I faced the same problem. The solution was to load both results and determine what to use after the query (I know it has performance downside), but at least you can do it temporarily if deadline attacks you:

At the LINQ side

  var Games = context.Games.Select(a => new GameModel
        {
            // carries type1 results
            Members = a.UsersInGames.Where(b => b.GameID == a.ID && b.StatusID == 1).Select(c => new Member
            {
                ID = c.UserID,
                email = c.UserInfo.EmailAddress,
                screenName = c.UserInfo.ScreenName
            })),

             //You need to create this temporary carrier to carry type 2 results
             MembersOfType2 = a.Teams.Where(b => b.GameID == a.ID).SelectMany(b => b.UsersInTeams.Where(c => c.StatusID == 1)).Select(d => new Member
                {
                    ID = d.UserID,
                    email = d.UserInfo.EmailAddress,
                    screenName = d.UserInfo.ScreenName
                })))
            })
        }

After that you may loop Gamesand make the assignment Members = MembersOfType2 if Type == 1 for a certain game.