【问题标题】:Error: Object cannot be cast from DBNull to other types when running through for-loop VB.NET错误:通过 for-loop VB.NET 运行时,无法将对象从 DBNull 转换为其他类型
【发布时间】:2013-07-19 20:38:16
【问题描述】:

我对空值有疑问。我需要一个 if 来检查 2 个值是否为空。如果我第一次循环,一切都很好。当我第二次循环时,'oTableTemp.Rows(i)("ProspectielijstId").ToString() = ""' 出现错误。我已经绝对尝试了一切。我试过 DbNull.Value,什么都没有,... 这是完整的代码:

    For i As Integer = 0 To oTableTemp.Rows.Count - 1 Step 1

        If (Convert.ToInt32(oTableTemp.Rows(i)("OpleidingsId")) = 0 And oTableTemp.Rows(i)("ProspectielijstId").ToString() = "" And oTableTemp.Rows(i)("ActieId") = specialeactieId) Then
            cString &= "SELECT * FROM AITest..SpecialeActie WHERE SpecialeActie.ActieId = " + clGlobalsData.G_FieldN(specialeactieId)
            Exit For
        ElseIf (oTableTemp.Rows(i)("ProspectielijstId").ToString() IsNot "" And oTableTemp.Rows(i)("ActieId") = specialeactieId) Then
            cString &= "    SELECT KlantProspectAlgemeen.Nummer, SpecialeActie.Titel, SpecialeActie.Inhoud, SpecialeActie.Link " & _
            "FROM (AITest..SpecialeActie INNER JOIN AITest..t_ProspectieLijst ON t_ProspectieLijst.NaamLijst= " & _
            "SpecialeActie.ProspectielijstID) INNER JOIN AITest..KlantProspectAlgemeen ON t_ProspectieLijst.Nummer=KlantProspectAlgemeen.Nummer WHERE SpecialeActie.ActieId = " + clGlobalsData.G_FieldN(specialeactieId)
            Exit For
        ElseIf (Convert.ToInt32(oTableTemp.Rows(i)("OpleidingsId")) <> 0 And oTableTemp.Rows(i)("ActieId") = specialeactieId) Then
            cString &= "SELECT KlantProspectAlgemeen.Nummer, SpecialeActie.Titel, SpecialeActie.Inhoud, SpecialeActie.Link " & _
            "FROM (AITest..SpecialeActie INNER JOIN AITest..Cursus ON Cursus.NummerInternCursus=SpecialeActie.OpleidingsID " & _
            "INNER JOIN AITest..CursusEmailmarketing ON Cursus.NummerInternCursus = CursusEmailmarketing.NummerInternCursus " & _
            "INNER JOIN AITest..t_ProspectieLijst ON t_ProspectieLijst.NaamLijst=CursusEmailmarketing.ProspectielijstID) " & _
            "INNER JOIN AITest..KlantProspectAlgemeen ON t_ProspectieLijst.Nummer= KlantProspectAlgemeen.Nummer WHERE SpecialeActie.ActieId = " + clGlobalsData.G_FieldN(specialeactieId)
            Exit For
        End If
    Next

请帮帮我,我很绝望..

【问题讨论】:

    标签: vb.net for-loop null


    【解决方案1】:

    首先,我不确定究竟是什么导致了错误,但是,这里有一些一般提示可以帮助找到错误的原因并修复它:

    我建议使用DataRowField 扩展方法,它是强类型的,也支持可空类型。它会自动将DBNull.Value 转换为适当的可为空类型。

    您还应该使用AndAlso 而不是And。如果第一部分已经是False,前者将不会执行第二部分,而后者将始终执行这两个部分,这可能会导致这样的错误。

    考虑一下:

    Dim str As String = Nothing
    If str IsNot Nothing And str.Length = 0 Then
       ' boooom
    End If
    

    这行得通:

    If str IsNot Nothing AndAlso str.Length = 0 Then
        ' no booom 
    End If
    

    这里的 sql 部分向您展示了一个更具可读性的示例:

    For Each row As DataRow In oTableTemp.Rows
        Dim OpleidingsId = row.Field(Of Int32)("OpleidingsId")
        Dim ProspectielijstId = row.Field(Of String)("ProspectielijstId")
        Dim ActieId = row.Field(Of Int32)("ActieId")
    
        If OpleidingsId = 0 AndAlso String.IsNullOrWhiteSpace(ProspectielijstId) AndAlso ActieId = specialeactieId Then
            cString = "SELECT * FROM AITest..SpecialeActie WHERE ..."
        End If
    

    注意你也对SQL-Injection开放,使用SQL-Parameters!

    【讨论】:

    • 当我第二次点击 if 时仍然出现异常
    • 现在他在 'Dim OpleidingsId = row.Field(Of Int32)("OpleidingsId")' 上给出了一个例外。这是一个例外:无法将 DBNull.Value 转换为类型“System.Int32”。请使用可为空的类型。
    • 您可以将 OpleidingsId 声明为可为空。试试像 Dim OpleidingsId? = row.Field(Of Int32)("OpleidingsId")。您可能必须将其转换为整数类型我不确定,试一试
    • @CharlotteVancraeynest:这就是我想在上面提出的建议。在适当的时候使用可为空的类型。我不知道哪一列可以为空。 Dim OpleidingsId = row.Field(Of Int32?)("OpleidingsId")现在可以查看If OpleidingsId.HasValue Then Console.Write(OpleidingsId.Value)
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2022-12-04
    • 2013-08-23
    • 1970-01-01
    • 2012-06-22
    • 1970-01-01
    • 2011-08-31
    相关资源
    最近更新 更多