Eigenen Wertdatentyp erstellen

  • VB.NET

Es gibt 12 Antworten in diesem Thema. Der letzte Beitrag () ist von FreakJNS.

    Eigenen Wertdatentyp erstellen

    Hi,

    wie kann man einen eigenen Wertdatentyp erstellen,
    welcher nur werte von z.B. 1 bis 20 einnehmen kann?
    Bei Enum kann man ja keine Zahlen auflisten (ist ja klar)

    Danke,
    wincrash
    (\_/) Das ist Hase.
    (O.o) Kopiere Hase in deine Signatur
    (> <) und hilf ihm so auf seinem Weg zur Weltherrschaft.
    Hey,

    vielleicht hilft Dir das ein bisschen weiter.

    stackoverflow.com/questions/39…rimitive-data-type-in-net
    Die Unendlichkeit ist weit. Vor allem gegen Ende. ?(
    Manche Menschen sind gar nicht dumm. Sie haben nur Pech beim Denken. 8o
    Habe ich bisher noch nie gesehen, dass jemand das so gemacht hat und echt eher hässlich :P. Enums sind eher dazu da, sinnvolle Konstanten zu definieren. Zumal kann man auch Enums instanzieren, die keine im Enum definierten Werte enthalten.
    Normalerweise genügt eine Abfrage auf den gültigen Wertebereich und eine ArgumentOutOfRangeException oder dergleichen.

    Gruß
    ~blaze~
    @ErfinderdesRades: Ja das war auch mein lösungsansatz - nur, wie schon von dir gesagt: nicht sehr hübsch
    @~blaze~: Ich möchte eine Function machen, welche nur werte von 1 bis 20 akzeptiert und sonst ne überladung
    bei der code-programmierung auslöst.

    wie soll ich denn ausserhalb von einer function eine if-schleife an einen byte-wert koppeln?

    wincrash

    edit: danke spaceyx, aber ich versteh das nicht richtig - vielleicht stell ich mich auch einfach nur dämlich an :/
    (\_/) Das ist Hase.
    (O.o) Kopiere Hase in deine Signatur
    (> <) und hilf ihm so auf seinem Weg zur Weltherrschaft.
    Naja, dafür einfach einen Beispieltext verfassen und den Wertebereich abfragen.

    VB.NET-Quellcode

    1. Public Shared Function Test(ByVal arg As Integer) As String
    2. If arg >= 1 AndAlso arg <= 20
    3. Return arg.ToString()
    4. Else
    5. Throw New ArgumentOutOfRangeException("arg")
    6. End Function

    so macht mans halt normalerweise. Evtl. noch mit einer schöneren Message.

    Gruß
    ~blaze~
    In dem Link, den ich Dir gegeben habe, ist ein bisschen weiter unten ein komplettes Beispiel, was so ziemlich das ist, was Du möchtest.

    VB.NET-Quellcode

    1. Structure LimitedInt
    2. Implements IComparable(Of LimitedInt)
    3. Implements IEquatable(Of LimitedInt)
    4. Private m_Value As Integer 'treat the default, 0 as being really 1'
    5. Public ReadOnly Property Value() As Integer
    6. Get
    7. Return If(m_Value = 0, 1, m_Value)
    8. End Get
    9. End Property
    10. Public Sub New(ByVal value As Integer)
    11. If value < 1 Or value > 10 Then
    12. Throw New ArgumentOutOfRangeException("value")
    13. End If
    14. m_Value = value
    15. End Sub
    16. Public Function CompareTo(ByVal other As LimitedInt) As Integer _
    17. Implements System.IComparable(Of LimitedInt).CompareTo
    18. Return Me.Value - other.Value
    19. End Function
    20. Public Overloads Function Equals(ByVal other As LimitedInt) As Boolean _
    21. Implements System.IEquatable(Of LimitedInt).Equals
    22. Return Me.Value = other.Value
    23. End Function
    24. Public Overrides Function GetHashCode() As Integer
    25. Return Value.GetHashCode
    26. End Function
    27. Public Overrides Function Equals(ByVal obj As Object) As Boolean
    28. If TypeOf obj Is LimitedInt Then Return CType(obj, LimitedInt) = Me
    29. End Function
    30. Public Shared Operator =(ByVal left As LimitedInt, _
    31. ByVal right As LimitedInt) As Boolean
    32. Return left.Equals(right)
    33. End Operator
    34. Public Shared Operator <>(ByVal left As LimitedInt, _
    35. ByVal right As LimitedInt) As Boolean
    36. Return Not (left = right)
    37. End Operator
    38. Public Shared Operator +(ByVal left As LimitedInt, _
    39. ByVal right As LimitedInt) As LimitedInt
    40. Dim temp As Integer = left.Value + right.Value
    41. Select Case temp
    42. Case 1 To 10 : Return New LimitedInt(temp)
    43. Case Else : Throw New OverflowException
    44. End Select
    45. End Operator
    46. Public Shared Operator -(ByVal left As LimitedInt, _
    47. ByVal right As LimitedInt) As LimitedInt
    48. Dim temp As Integer = left.Value - right.Value
    49. Select Case temp
    50. Case 1 To 10 : Return New LimitedInt(temp)
    51. Case Else : Throw New OverflowException
    52. End Select
    53. End Operator
    54. Public Shared Operator *(ByVal left As LimitedInt, _
    55. ByVal right As LimitedInt) As LimitedInt
    56. Dim temp As Integer = left.Value * right.Value
    57. Select Case temp
    58. Case 1 To 10 : Return New LimitedInt(temp)
    59. Case Else : Throw New OverflowException
    60. End Select
    61. End Operator
    62. Public Shared Operator /(ByVal left As LimitedInt, _
    63. ByVal right As LimitedInt) As Double
    64. Return left.Value / right.Value
    65. End Operator
    66. Public Shared Operator \(ByVal left As LimitedInt, _
    67. ByVal right As LimitedInt) As LimitedInt
    68. Dim temp As Integer = left.Value \ right.Value
    69. Select Case temp
    70. Case 1 To 10 : Return New LimitedInt(temp)
    71. Case Else : Throw New OverflowException
    72. End Select
    73. End Operator
    74. Public Shared Operator Mod(ByVal left As LimitedInt, _
    75. ByVal right As LimitedInt) As LimitedInt
    76. Dim temp As Integer = left.Value Mod right.Value
    77. Select Case temp
    78. Case 1 To 10 : Return New LimitedInt(temp)
    79. Case Else : Throw New OverflowException
    80. End Select
    81. End Operator
    82. Public Shared Operator And(ByVal left As LimitedInt, _
    83. ByVal right As LimitedInt) As LimitedInt
    84. Dim temp As Integer = left.Value And right.Value
    85. Select Case temp
    86. Case 1 To 10 : Return New LimitedInt(temp)
    87. Case Else : Throw New OverflowException
    88. End Select
    89. End Operator
    90. Public Shared Operator Or(ByVal left As LimitedInt, _
    91. ByVal right As LimitedInt) As LimitedInt
    92. Dim temp As Integer = left.Value Or right.Value
    93. Select Case temp
    94. Case 1 To 10 : Return New LimitedInt(temp)
    95. Case Else : Throw New OverflowException
    96. End Select
    97. End Operator
    98. Public Shared Operator Xor(ByVal left As LimitedInt, _
    99. ByVal right As LimitedInt) As LimitedInt
    100. Dim temp As Integer = left.Value Xor right.Value
    101. Select Case temp
    102. Case 1 To 10 : Return New LimitedInt(temp)
    103. Case Else : Throw New OverflowException
    104. End Select
    105. End Operator
    106. Public Shared Operator ^(ByVal left As LimitedInt, _
    107. ByVal right As LimitedInt) As Double
    108. Return left.Value ^ right.Value
    109. End Operator
    110. Public Shared Operator <(ByVal left As LimitedInt, _
    111. ByVal right As LimitedInt) As Boolean
    112. Return left.Value < right.Value
    113. End Operator
    114. Public Shared Operator >(ByVal left As LimitedInt, _
    115. ByVal right As LimitedInt) As Boolean
    116. Return left.Value > right.Value
    117. End Operator
    118. Public Shared Operator <=(ByVal left As LimitedInt, _
    119. ByVal right As LimitedInt) As Boolean
    120. Return left.Value <= right.Value
    121. End Operator
    122. Public Shared Operator >=(ByVal left As LimitedInt, _
    123. ByVal right As LimitedInt) As Boolean
    124. Return left.Value >= right.Value
    125. End Operator
    126. Public Shared Widening Operator CType(ByVal left As LimitedInt) As Integer
    127. Return left.Value
    128. End Operator
    129. Public Shared Narrowing Operator CType(ByVal left As Integer) As LimitedInt
    130. Return New LimitedInt(left)
    131. End Operator
    132. End Structure
    Die Unendlichkeit ist weit. Vor allem gegen Ende. ?(
    Manche Menschen sind gar nicht dumm. Sie haben nur Pech beim Denken. 8o
    Stimmt schon, aber ich finds schöner, es in der Dokumentation festzuhalten. Wenn es nicht explizit klar ist, könnte man auch noch Konstanten definieren, die Min und Max bereitstellen, aber im Normalfall ist das nicht das Problem. Der Programmierer muss halt verstehen was er macht. Das Enum würde ich nur nehmen, wenn die einzelnen Aktionen wirklich für konstante Ausdrücke stehen und diese in einem Delegaten-Array kapseln.

    Gruß
    ~blaze~
    Mega! xD
    Ich frage mich, wie das überhaupt funktionieren soll. Ich meine eine Variable vom Typ MeinInterger0bis20 hat einen anderen Typ als MeinInteger21bis500. Darum funktioniert das angestrebte anzeigen mehrerer Überladungen auch. Wundertoll. Nur muss ich doch zur Entwicklungszeit festlegen, welche Werte in welchen Typ gespeichert werden - irgendwo muss die Entscheidung getroffen werden, welcher Typ einem Wert zugeordnet wird. Und das passiert mit einer einfachen If-Abfrage wie blaze sagt. Genau desswegen kenne ich den Zustand und kann entsprechend reagieren OHNE das die Variable einen bestimmten Typ zur Unterscheidung haben muss.
    Statt einen workaround über eigene Bastel-Datentypen zu machen könnte man hier einfach die passende Methode aufrufen (anderer Mehtodennamen/auf Überladungen verzichten) oder die Methode selbst entscheiden lassen, was sie tut.

    Die Lösung mit der Enum ist auf jeden Fall besser als die eines eigenen Datentyps, würde ich aber auch nicht einsetzten weil man wieder zur Entwicklungszeit wissen muss welchen Wert man nun welcher Enum zuweisen kann (If-Abfrage) - man muss nicht anhand des Datentyps entscheiden.

    Hoffe man versteht was ich meine und das es so stimmt. Unter Strict Off (ganz böse wenn oben nicht Option Strict ON steht!!) geht vermutlich "so einiges" xDD
    trotzdem interessant die Sache mit dem eigenen Integer. lg