2

I'm using .NET 3.5 In my DataLayer class I have references of System.Core,System.Data.Linq, System.Data.DataSetExtensions. But I cantnot use this feature in Linq query if I have Option Strict ON:

    Dim query = From st In db.Students _
         From c In db.Countries.Where(Function(c) c.Id = st.CountryId).DefaultIfEmpty _
         From r In db.Rooms.Where(Function(r) r.Id = st.RoomId).DefaultIfEmpty _
         From b In db.Buildings.Where(Function(b) b.Id = r.BuildingId).DefaultIfEmpty _
         From es In db.Essays.Where(Function(es) es.StudentId = st.Id).DefaultIfEmpty _
         Select st.Id, st.FullName, c.CountryName, r.RoomNumber, b.BuildingName, es.Eassay

It will yield the following error:

Overload resolution failed because no accessible 'Where' can be called with these arguments:
    Extension method 'Public Function Where(predicate As System.Linq.Expressions.Expression(Of System.Func(Of Country, Integer, Boolean))) As System.Linq.IQueryable(Of Country)'

defined in 'System.Linq.Queryable': Nested function does not have the same signature as delegate 'System.Func(Of Country, Integer, Boolean)'.

Extension method 'Public Function Where(predicate As System.Linq.Expressions.Expression(Of System.Func(Of Country, Boolean))) As System.Linq.IQueryable(Of Country)' defined in 'System.Linq.Queryable': Option Strict On disallows implicit conversions from 'Boolean?' to 'Boolean'.
    Extension method 'Public Function Where(predicate As System.Func(Of Country, Integer, Boolean)) As System.Collections.Generic.IEnumerable(Of Country)' defined in 'System.Linq.Enumerable': Nested function does not have the same signature as delegate 'System.Func(Of Country, Integer, Boolean)'.
    Extension method 'Public Function Where(predicate As System.Func(Of Country, Boolean)) As System.Collections.Generic.IEnumerable(Of Country)' defined in 'System.Linq.Enumerable': Option Strict On disallows implicit conversions from 'Boolean?' to 'Boolean'..........

The "Where" clause is Member of System.Linq.Queryable

Public Shared Function Where(Of TSource)(ByVal source As System.Linq.IQueryable(Of TSource), ByVal predicate As System.Linq.Expressions.Expression(Of System.Func(Of TSource, Boolean))) As System.Linq.IQueryable(Of TSource)

And "DefaultIfEmpty" is Member of System.Linq.Queryable

Public Shared Function DefaultIfEmpty(Of TSource)(ByVal source As System.Linq.IQueryable(Of TSource)) As System.Linq.IQueryable(Of TSource)

If I set Option Strict OFF, there's no problem.

How to use these System.Linq extension methods in VB.NET project with Option Strict ON ? Thank you

Narazana
  • 1,940
  • 15
  • 57
  • 88
  • If you get really bored of using Strict, try Option Infer On to enable type inference. Just an idea, if it breaks rules/patterns then ignore this :) http://msdn.microsoft.com/en-us/library/bb384665.aspx – Tom Feb 02 '11 at 11:23

1 Answers1

5

Looks like CountryId is a nullable value type, hence

c.CountryId = st.CountryId

will be a nullable boolean instead of a regular boolean.

Try something like this

From st In db.Students _
From c In db.Countries.Where(Function(c) If(c.CountryId = st.CountryId, False)) _
Select st.FirstName, c.CountryName

BTW, it's seems your looking for a group join anyhow:

From s In db.Students
Group Join c In db.Countries On s.CountryID Equals c.CountryID Into Group
From g In Group.DefaultIfEmpty
Select New With {.Name = s.Name, .CountryName = If(g IsNot Nothing, g.CountryName, "")}
sloth
  • 99,095
  • 21
  • 171
  • 219
  • Please see my update query. I need to modify those query so it works with Option Strict ON. If I used this "Join c in Countries On st.CountryID Equals c.CountryID" I get only those records that have CountryId. But I want to get all students that's why I came to use db.Countries.Where(Function(c) c.Id = st.CountryId).DefaultIfEmpty but it won't work with Option Strick ON. If you'd like to see DB structure, please go here http://stackoverflow.com/questions/4870964 – Narazana Feb 02 '11 at 10:39
  • Thanks for the DB structure, that makes things clearer. As I said, your problem is that CountryID in Students is nullable. I'll update my answer... – sloth Feb 02 '11 at 10:58
  • If there's any option to the query and produce the same result I'd like to try it as well. Thanks. – Narazana Feb 02 '11 at 11:06
  • you could just alter your where-clause to use 'If(c.CountryId = st.CountryId, False)' instead of 'c.CountryId = st.CountryId', since the former one yields False to the where-clause if st.CountryId is nothing. – sloth Feb 02 '11 at 11:25
  • I tried your First Suggestion but it worked only if select Students, Countries, and Rooms. When I added another line to select Essays table like this From es In db.Essays.Where(Function(es) If(es.StudentId = st.Id, False)).DefaultIfEmpty _ it's throw same error. Is there's any reason why it's like this? – Narazana Feb 02 '11 at 11:31
  • Your second suggestion is superb. Thank you very much. :D – Narazana Feb 02 '11 at 11:46