I have the following Linq lambda expression:
private IEnumerable<SubjectSelectorSubjectGroup> GetSubjectList()
{
User user = db.Users.Find(WebSecurity.CurrentUserId);
return db.RequiredSubjects.Where(r => !r.Subject.Name.Contains("Home"))
.GroupBy(r => r.Subject)
.OrderByDescending(r => r.Count())
.Select(r => new SubjectSelectorSubjectGroup()
{
SubjectId = r.Key.SubjectId,
SubjectName = r.Key.Name,
IsInFavourites = HttpContext.Current.Request.IsAuthenticated &&
(user.Elective1 != null && user.Elective1.SubjectId == r.Key.SubjectId ||
user.Elective2 != null && user.Elective2.SubjectId == r.Key.SubjectId ||
user.Elective3 != null && user.Elective3.SubjectId == r.Key.SubjectId),
Occurrences = r.Count()
});
}
When the user is not logged in then the user
variable in this function is null. This should not be a problem becuase short-circuit boolean evaluation should deal with this. The problem is, it doesn't! Instead, a System.NullReferenceException
is thrown.
When the user is null HttpContext.Current.Request.IsAuthenticated
returns false. I have checked this by commenting out the bracketed section that references the user
variable, and then expression evaluates correctly.
Does anyone know why Linq to Sql
tries to dereference the user
variable in this situation when it shouldn't actually be necessary? Does anyone have a work around for this issue?
Language Integrated Query (LINQ) is feature of Visual Studio that gives you the capabilities yo query on the language syntax of C#, so you will get SQL kind of queries. And Lambda expression is an anonymous function and is more of a like delegate type.
A lambda expression is a convenient way of defining an anonymous (unnamed) function that can be passed around as a variable or as a parameter to a method call. Many LINQ methods take a function (called a delegate) as a parameter.
Short-Circuit Evaluation: Short-circuiting is a programming concept in which the compiler skips the execution or evaluation of some sub-expressions in a logical expression. The compiler stops evaluating the further sub-expressions as soon as the value of the expression is determined.
The conditional logical OR operator || , also known as the "short-circuiting" logical OR operator, computes the logical OR of its operands. The result of x || y is true if either x or y evaluates to true . Otherwise, the result is false . If x evaluates to true , y is not evaluated.
The entire expression is translated to and evaluated as SQL, which means that the &&
operator is not short circuited as expected.
You can solve the problem by building a list or array of the ElectiveX.SubjectId
that you want to search for and then use tmpList.Contains(r.Key.SubjectId)
in the query. That will be translated into a WHERE IN (...)
SQL expression.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With