VB.NET结构和没什么 - 问题

时间:2010-07-02 20:49:31

标签: .net vb.net data-structures structure nothing

我在使用在VB.NET中返回Nothing的Structures和函数时遇到了一些麻烦。

让我试着用这段代码解释一下:

Public Class Form1
    Structure Test
        Dim field1 As String
    End Structure

    Private Function Foo() As Test
        Return Nothing
    End Function

    Private Sub Form1_Load(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles MyBase.Load
        Dim st As Test = Foo()
    End Sub
End Class

在上一段代码中,当我因Foo函数返回Nothing时,我希望 st Nothing 。但事实并非如此。

然后我在MSDN文档中找到了:

  

为变量赋值Nothing将其设置为其声明类型的默认值。如果该类型包含变量成员,则它们都设置为默认值。

所以我发现当我将 Nothing 分配给一个结构时,它的所有成员都被设置为默认值,而不是结构本身。

另外,我尝试通过声明 st 为Nullable类型:

    Dim st As Nullable(Of Test) = Foo()  

但是,我仍然无法使用以下方法检查 st 是否为Nothing:

    If st Is Nothing Then  

    If st.Equals(Nothing) Then

所以,问题:
1 - 是否可以将 Nothing 分配给结构而不是其成员?
2 - 如何检查返回结构值是否 Nothing

3 个答案:

答案 0 :(得分:17)

结构是值类型,它不能是Nothing。 Nullable类型可以解决您的问题,在类型名称后面添加一个问号,使其变短和活泼。这是一个例子:

Module Module1

    Structure Test
        Dim field1 As String
    End Structure

    Private Function Foo() As Test?
        Return Nothing
    End Function

    Sub Main()
        Dim st As Test? = Foo()
        Debug.Assert(st is Nothing)
    End Sub

End Module

答案 1 :(得分:11)

.NET Framework中经常使用前两个方法。您使用的方法取决于您的要求。如果不经常测试结构,我将使用方法#3。对于频繁测试,如果方法#2不适合“空”测试,我将使用方法#1。例如,Point结构将空点定义为{x = 0,y = 0},我认为这是不正确的。因此,我会在我的点结构实现中使用第一种方法。

方法1:定义Empty对比测试的测试

添加共享Test以用于空比较。

Structure Test
    Public Shared Empty As Test = New Test
    Dim field1 As String 
End Structure 

测试为:

If st = Test.Empty Then

方法2:定义IsEmpty测试属性

根据结构的内部状态定义IsEmpty属性。

Structure Test 
    Public ReadOnly Property IsEmpty As Boolean
        Get
            Return Len(field1) = 0
        End Get
    End Property
    Dim field1 As String 
End Structure 

测试为:

If st.IsEmpty Then

方法3:使用Nullable(Of T)

定义为:

Dim st As Test? = Foo() 
'--or--
Dim st As Nullable(Of Test) = Foo()

测试为:

If st Is Nothing Then
'--or--
If st.HasValue = False Then

注意

我没有测试过上面的代码,也没有访问我的代码库。

启示

使用他们发布的源代码或使用 .NET Reflector 查看Microsoft的PointColor结构。

答案 2 :(得分:0)

没有“分配结构而不是结构”的概念。

这听起来非常像你应该看nullable value typesNullable(Of T) - 如果你需要能够代表值类型缺少“真实”值,那就是正是它被发明的原因。

例如考虑ByteByte值可以包含256个值(0-255)中的任何一个。如果你为它赋值Nothing,它实际上会使它为0.它不能使它“某些值不在0-255范围内”,因为它将存储为一个字节。我认为VB 允许你在这里使用Nothing有点不幸,实际上......因为哲学上“缺失”值和值0确实是非常不同的事情。

无论如何,可空值的类型包含“普通”值类型,并提供一个额外的布尔值来表示是否真的是否存在有用的值。