[VB.NET] Sorting Array of Custom Class objects-VBForums
Results 1 to 4 of 4

Thread: [VB.NET] Sorting Array of Custom Class objects

  1. #1

    Thread Starter
    Noodly Appendage wossname's Avatar
    Join Date
    Aug 2002
    Location
    #!/bin/bash
    Posts
    5,669

    [VB.NET] Sorting Array of Custom Class objects

    Lets say you are writing a card game and you need to be able to sort a player's cards into numerical and suit order.

    You have written a PlayingCard class, and you have to find a way of sorting by these 2 criteria.

    The .Net (OOP) way is to make that class implement the IComparable interface. This simply adds a function that decides if one class instance is 'greater then, less than or equal to' another instance of the same class. Write your sorting rules into this function body and that is. You don't have to worry about moving items into the right places in the array, or type conversion problems, or anything like that. The Array.Sort() function calls your implementation of the IComparable interface and communicates directly with it without your intervention.

    Here is a nice example I just cooked up.
    (The important parts are highlighted in red).


    Code:
    Module Module1
    
    	Sub Main()
    
    		Dim Deck() As PlayingCard = New PlayingCard(99) {}
    		Dim i As Integer
    		Dim r As Random = New Random
    
    		For i = 0 To 99		  'randomize the array
    			Deck(i) = New PlayingCard(r.Next(PlayingCard.CARDVALUE.Ace, PlayingCard.CARDVALUE.King + 1), r.Next(PlayingCard.CARDSUIT.Spades, PlayingCard.CARDSUIT.Diamonds + 1))
    		Next i
    
    		PlayingCard.AcesHigh = True
    		Array.Sort(Deck)
    
    		For i = 0 To 99
    			Console.WriteLine(Deck(i))
    		Next i
    
    		Console.ReadLine()
    
    	End Sub
    
    End Module
    
    Public Class PlayingCard
    	Implements IComparable	'IMPORTANT
    
    #Region "Game Specific"
    #Region "Enums"
    	Public Enum CARDVALUE
    		Ace = 1
    		Two = 2
    		Three = 3
    		Four = 4
    		Five = 5
    		Six = 6
    		Seven = 7
    		Eight = 8
    		Nine = 9
    		Ten = 10
    		Jack = 11
    		Queen = 12
    		King = 13
    		HighAce = 14
    	End Enum
    	Public Enum CARDSUIT
    		Spades = 0
    		Hearts = 1
    		Clubs = 2
    		Diamonds = 3
    	End Enum
    #End Region
    #Region "Shared"
    	Public Shared AcesHigh As Boolean = False
    #End Region
    #Region "Member Data"
    	Private _Value As CARDVALUE = CARDVALUE.Ace
    	Private _Suit As CARDSUIT = CARDSUIT.Spades
    #End Region
    
    	Public Property Value() As CARDVALUE
    		Get
    			Return _Value
    		End Get
    		Set(ByVal RHS As CARDVALUE)
    			If RHS = CARDVALUE.HighAce Then Throw New ArgumentException("Cannot set Value to HighAce directly, set Value to Ace and set AcesHigh variable to True")
    			_Value = RHS
    		End Set
    	End Property
    	Public Property Suit() As CARDSUIT
    		Get
    			Return _Suit
    		End Get
    		Set(ByVal RHS As CARDSUIT)
    			_Suit = RHS
    		End Set
    	End Property
    	Public ReadOnly Property IsHighAce() As Boolean
    		Get
    			Return (_Value = CARDVALUE.Ace) And AcesHigh
    		End Get
    	End Property
    	Public ReadOnly Property IsRoyalty() As Boolean
    		Get
    			Return (_Value >= CARDVALUE.Jack) And (_Value <= CARDVALUE.King)
    		End Get
    	End Property
    	Public Overrides Function ToString() As String
    
    		Dim s As String
    
    		Select Case _Value
    			Case CARDVALUE.Ace
    				s = "Ace of "
    			Case CARDVALUE.Two
    				s = "Two of "
    			Case CARDVALUE.Three
    				s = "Three of "
    			Case CARDVALUE.Four
    				s = "Four of "
    			Case CARDVALUE.Five
    				s = "Five of "
    			Case CARDVALUE.Six
    				s = "Six of "
    			Case CARDVALUE.Seven
    				s = "Seven of "
    			Case CARDVALUE.Eight
    				s = "Eight of "
    			Case CARDVALUE.Nine
    				s = "Nine of "
    			Case CARDVALUE.Ten
    				s = "Ten of "
    			Case CARDVALUE.Jack
    				s = "Jack of "
    			Case CARDVALUE.Queen
    				s = "Queen of "
    			Case CARDVALUE.King
    				s = "King of "
    		End Select
    
    		Select Case _Suit
    			Case CARDSUIT.Spades
    				s &= "Spades"
    			Case CARDSUIT.Hearts
    				s &= "Hearts"
    			Case CARDSUIT.Clubs
    				s &= "Clubs"
    			Case CARDSUIT.Diamonds
    				s &= "Diamonds"
    		End Select
    
    		Return s
    
    	End Function
    
    #End Region
    
    	Public Sub New(ByVal itsValue As CARDVALUE, ByVal itsSuit As CARDSUIT)
    		Value = itsValue
    		Suit = itsSuit
    	End Sub
    
    	Public Function CompareTo(ByVal obj As Object) As Integer Implements System.IComparable.CompareTo
    
    		'where the Sorting logic is run
    
    		'Basically says: "if ME greater than the obj card then return 1, if equal return 0 and if less than, return -1"
    
    		If Not TypeOf obj Is PlayingCard Then Throw New ArgumentException 'make sure obj is a card before continuing
    
    		Dim temp As PlayingCard = CType(obj, PlayingCard)
    		Dim vObj As CARDVALUE = temp.Value
    		Dim vMe As CARDVALUE = _Value
    		Dim s As CARDSUIT = temp.Suit
    
    		If _Suit < s Then		  'suits take precedence
    			Return -1
    		ElseIf _Suit > s Then
    			Return 1
    		Else
    			If AcesHigh Then		  'some games require aces to have a value of 14 rather than 1, hence "Aces High"
    				If vObj = CARDVALUE.Ace Then vObj = CARDVALUE.HighAce
    				If vMe = CARDVALUE.Ace Then vMe = CARDVALUE.HighAce
    			End If
    			'if suite are the same, check the card numbers...
    			If vMe < vObj Then
    				Return -1
    			ElseIf vMe > vObj Then
    				Return 1
    			Else
    				Return 0				   'cards are identical (if you are using more than 1 deck deck of cards in a program)
    			End If
    			End If
    
    	End Function
    
    End Class
    Copy this code into a console app and run it. It also demonstrates the overriding of the Tostring() function.

    The output looks like this...
    I don't live here any more.

  2. #2
    Banned WonkoTheSane's Avatar
    Join Date
    Nov 2004
    Location
    Jersey, nr France
    Posts
    8
    That works fine!

    Nice work wossname.

  3. #3
    Banned plenderj's Avatar
    Join Date
    Jan 2001
    Location
    Dublin, Ireland
    Posts
    10,359

  4. #4
    Super Moderator Hack's Avatar
    Join Date
    Aug 2001
    Location
    Searching for mendhak
    Posts
    58,334

    Re: [VB.NET] Sorting Array of Custom Class objects

    Moved to Games CodeBank
    Please use [Code]your code goes in here[/Code] tags when posting code.
    When you have received an answer to your question, please mark it as resolved using the Thread Tools menu.
    Before posting your question, did you look here?
    Got a question on Linux? Visit our Linux sister site.
    I dont answer coding questions via PM or EMail. Please post a thread in the appropriate forum section.

    Creating A Wizard In VB.NET
    Paging A Recordset
    What is wrong with using On Error Resume Next
    Good Article: Language Enhancements In Visual Basic 2010
    Upgrading VB6 Code To VB.NET
    Microsoft MVP 2005/2006/2007/2008/2009/2010/2011/2012/Defrocked

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •  



Featured


Click Here to Expand Forum to Full Width

Survey posted by VBForums.