Vb.net 如何在LINQtoSQL中优雅地处理空外键?

Vb.net 如何在LINQtoSQL中优雅地处理空外键?,vb.net,linq-to-sql,Vb.net,Linq To Sql,在我的数据库中,特许权与公司有多对一的关系(每个特许权都有一个FirmID)。SqlMetal捕获了这种关系并生成了适当的类,因此每个让步都有一个固定元素。我反对一个查询(此处简化),该查询返回特许权列表以及相应公司的信息: From c as Concession in Db.Concessions _ Select _ c.ConcessionID, _ c.Title, _ c.Firm.Title 问题是,在某些情况下,特许权没有分配给公司(c.FirmID为null

在我的数据库中,特许权与公司有多对一的关系(每个特许权都有一个FirmID)。SqlMetal捕获了这种关系并生成了适当的类,因此每个让步都有一个固定元素。我反对一个查询(此处简化),该查询返回特许权列表以及相应公司的信息:

From c as Concession in Db.Concessions _
Select _
   c.ConcessionID, _
   c.Title, _
   c.Firm.Title
问题是,在某些情况下,特许权没有分配给公司(c.FirmID为null),因此c.Firm什么都不是,我得到的
对象没有设置为实例
等等

我可以通过如下方式进行连接来解决此问题:

From c As Concession In Db.Concessions _
Join f As Firm In Db.Firms On f.FirmID Equals c.FirmID _
Select _
    c.ConcessionID, _
    c.Title, _
    Firm_Title = f.Title 
当FirmID为null时(Firm_Title只是一个空字符串),这不会引发错误,但它并不优雅:它不是面向对象的,并且它没有利用Linq to SQL已经捕获的所有关系智能


有没有更优雅的方法来处理这种情况?

您的第二个示例是进行内部联接。它不会返回FirmID为空的特许权。在这种情况下,您要执行外部联接:


您的第二个示例是进行内部联接。它不会返回FirmID为空的特许权。在这种情况下,您要执行外部联接:


您从哪里得到错误

我刚刚完成了一个类似的LINQ查询(在VB.Net中),它工作得很好(将Title设置为null)

稍后您将不得不处理标题为空的问题,但这并不是一个真正的LINQ问题。 甚至在C#中也可以很容易地处理这个问题


Vb.net中的等效方法是使用Iif(),但我无法使其正常工作。

您从哪里得到错误

我刚刚完成了一个类似的LINQ查询(在VB.Net中),它工作得很好(将Title设置为null)

稍后您将不得不处理标题为空的问题,但这并不是一个真正的LINQ问题。 甚至在C#中也可以很容易地处理这个问题


在Vb.net中,等效的方法是使用Iif(),但我无法让它工作。

@James Curran:在实际执行查询时,我都会收到错误-例如,如果我将网格数据绑定到它,或者如果我将
.ToList
应用到它

VB.NET有一个新的真正的三元语法(仍然比C#更详细)。这实际上是有效的:

From c As Concession In db.Concessions _
Select _
    c.ConcessionID, _
    c.Title, _
    Firm_Title = If(c.Firm IsNot Nothing, c.Firm.Title, String.Empty) _

我对这种方法不是很满意——对我可能从外部表中使用的每个字段都这样做是一种痛苦。我很想知道为什么您的查询有效而我的查询无效——您的DataContext是由SqlMetal生成的吗?关系是从数据库推断出来的吗?

@James Curran:在实际执行查询的任何时候,我都会收到错误消息-例如,如果我将网格数据绑定到它,或者如果我将
.ToList
应用到它

VB.NET有一个新的真正的三元语法(仍然比C#更详细)。这实际上是有效的:

From c As Concession In db.Concessions _
Select _
    c.ConcessionID, _
    c.Title, _
    Firm_Title = If(c.Firm IsNot Nothing, c.Firm.Title, String.Empty) _

我对这种方法不是很满意——对我可能从外部表中使用的每个字段都这样做是一种痛苦。我很想知道为什么您的查询有效而我的查询无效——您的DataContext是由SqlMetal生成的吗?关系是从数据库推断出来的吗?

在对象构造函数中处理它

Public Property office() As String
            Get
                Return _office
            End Get
            Set(ByVal value As String)
                If value IsNot Nothing Then
                    _office = value
                Else
                    _office = String.Empty
                End If
            End Set
        End Property

在对象构造函数中处理它

Public Property office() As String
            Get
                Return _office
            End Get
            Set(ByVal value As String)
                If value IsNot Nothing Then
                    _office = value
                Else
                    _office = String.Empty
                End If
            End Set
        End Property

我想你也可以这样做:if(c.Firm.Title,String.Empty)No,如果c.Firm什么都不是,那么抛出“对象引用未设置为对象实例”。我想你也可以这样做:if(c.Firm.Title,String.Empty)No,抛出“对象引用未设置为对象实例”如果c.Firm什么都不是。构造函数是由SqlMetal自动生成的,我希望保持这种方式。构造函数是由SqlMetal自动生成的,我希望保持这种方式。