VB.NET Structs et rien - problèmes
-
02-10-2019 - |
Question
Je vais avoir quelques maux de tête en utilisant des structures et fonctions que rien de retour dans VB.NET.
Je vais essayer d'expliquer ici avec ce code:
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
Dans le code précédent, quand je retourne rien comme résultat de la fonction Foo je voudrais attendre que st Rien . Mais ce n'est pas ce qui se passe.
Alors j'ai trouvé dans la documentation MSDN:
Affectation Rien à un des ensembles de variables à la valeur par défaut pour son type déclaré. Si ce type contient des membres variables, ils sont tous à leurs valeurs par défaut.
Je découvre que quand je assign Rien à une structure, tous ses membres sont à leurs valeurs par défaut, au lieu de la struct lui-même.
En outre, j'ai essayé de faire st un type Nullable en déclarant:
Dim st As Nullable(Of Test) = Foo()
mais je ne peux toujours pas vérifier si st est rien en utilisant:
If st Is Nothing Then
ou
If st.Equals(Nothing) Then
Alors, questions:
1 - Est-il possible d'assigner Rien à la structure et non à ses membres
2 - Comment puis-je vérifier si une valeur struct de retour est Rien
La solution
structure A est un type de valeur, il ne peut être rien. Le type Nullable peut résoudre votre problème, mettre un point d'interrogation après le nom du type pour faire court et accrocheurs. Voici un exemple:
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
Autres conseils
Les deux premières méthodes suivantes sont fréquemment utilisées dans le .NET Framework. La méthode utilisée dépendra de vos besoins. Je vais utiliser la méthode # 3 si la structure testée rarement. Pour des tests fréquents, je vais utiliser la méthode # 1 si la méthode n ° 2 est non pas pour des tests « vide ». Par exemple, la structure Point
définit un point vide comme {x = 0, y = 0}, que je ne pense pas est correct. Par conséquent, je voudrais utiliser la première méthode dans ma mise en œuvre de la structure du point.
Méthode 1: Définir Test Empty
pour Test de comparaison
Ajouter Test
partagée à utiliser pour une comparaison-vide.
Structure Test
Public Shared Empty As Test = New Test
Dim field1 As String
End Structure
test comme:
If st = Test.Empty Then
Méthode 2: Définir la propriété IsEmpty
pour les tests
Définir une propriété IsEmpty
basée sur l'état interne de la structure.
Structure Test
Public ReadOnly Property IsEmpty As Boolean
Get
Return Len(field1) = 0
End Get
End Property
Dim field1 As String
End Structure
test comme:
If st.IsEmpty Then
Méthode 3: Utiliser Nullable (Of T)
Définir comme:
Dim st As Test? = Foo()
'--or--
Dim st As Nullable(Of Test) = Foo()
test comme:
If st Is Nothing Then
'--or--
If st.HasValue = False Then
Remarque
Je ne l'ai pas testé le code ci-dessus et je n'ai pas accès à mon code bibliothèque.
Inspiration
Jetez un coup d'oeil aux structures de Point
de Microsoft et Color
, en utilisant leur code source publié ou en utilisant NET Reflector .
Il n'y a pas de concept comme l'attribution « Rien à la structure et non à ses membres ».
Il ressemble beaucoup à vous devriez regarder nullable types de valeurs et Nullable(Of T)
- si vous devez être en mesure de représenter la absence d'une valeur "réelle" pour un type de valeur, que de avec précision la raison pour laquelle il a été inventé.
Prenons Byte
par exemple. Une valeur de Byte
peut avoir l'une des valeurs 256 (0-255). Si vous lui attribuez la Nothing
valeur, qui va effectivement rendre 0. Il ne peut pas faire « une valeur pas dans la plage 0-255 » comme il va être stocké un octet . Je considère comme un peu malheureux que VB ne vous permettent d'utiliser Nothing
ici, en fait ... parce que philosophiquement une « manquante » valeur et la valeur 0 sont des choses très différentes en effet.
De toute façon, les types de valeurs nullables envelopper les types de valeurs « normales » et fournir une valeur booléenne supplémentaire pour dire s'il y a vraiment une valeur d'utilité présente ou non.