Results 1 to 7 of 7

Thread: Array sorting

  1. #1

    Thread Starter
    New Member
    Join Date
    May 2001
    Posts
    14

    Question Array sorting

    I have an array in a custom type for my hockey game, for instance:

    aPlayer(i).PlayerID
    aPlayer(i).Firstname
    aPlayer(i).Lastname
    aPlayer(i).Weight

    There's about 30 different attributes for each player as you can imagine. I'm trying to sort the list by Weight, but I'm having real trouble wrapping my head around it. I obviously need to keep the numbers in the same place (i.e. even if aPlayer(0).PlayerID was last on the list, he needs to stay aPlayer(0)). I guess I can create another array called aSort and fill this with the same information as aPlayer..but I'm not sure how to sort it properly.

    Can I use a normal sorting routine? Because there's so many attributes, is it different? Can anyone post any sorting code that would be able to deal with this sort of array?

    Sorry, it's really confusing me.

    Thanks for your help in advance, sorry for the n00b question. Cheers

  2. #2
    Former Admin/Moderator MartinLiss's Avatar
    Join Date
    Sep 1999
    Location
    San Jose, CA
    Posts
    33,431
    You'll have to add more code for the 26 or so other fields in your UDT, but this is the basics.

    VB Code:
    1. Option Explicit
    2. Private Type aPlayer
    3.     PlayerID As String
    4.     Firstname As String
    5.     Lastname As String
    6.     Weight As Double
    7. End Type
    8. Private TestData(4) As aPlayer
    9.  
    10. Private Sub Form_Load()
    11.  
    12.     Dim temp As aPlayer
    13.     Dim bIsChange As Boolean
    14.     Dim intIndex As Integer
    15.  
    16.     TestData(0).PlayerID = "a"
    17.     TestData(0).Firstname = "Martin"
    18.     TestData(0).Lastname = "Liss"
    19.     TestData(0).Weight = 142
    20.    
    21.     TestData(1).PlayerID = "b"
    22.     TestData(1).Firstname = "John"
    23.     TestData(1).Lastname = "Weakling"
    24.     TestData(1).Weight = 98
    25.    
    26.     TestData(2).PlayerID = "c"
    27.     TestData(2).Firstname = "Tiny"
    28.     TestData(2).Lastname = "Jones"
    29.     TestData(2).Weight = 305
    30.    
    31.     TestData(3).PlayerID = "d"
    32.     TestData(3).Firstname = "Steve"
    33.     TestData(3).Lastname = "Stunning"
    34.     TestData(3).Weight = 205
    35.    
    36.     TestData(4).PlayerID = "e"
    37.     TestData(4).Firstname = "Grace"
    38.     TestData(4).Lastname = "Slick"
    39.     TestData(4).Weight = 180
    40.    
    41.     bIsChange = True
    42.     Do Until bIsChange = False
    43.         bIsChange = False
    44.         For intIndex = 0 To UBound(TestData) - 1
    45.             If TestData(intIndex).Weight > TestData(intIndex + 1).Weight Then
    46.                 bIsChange = True
    47.                 ' Swap the data
    48.                 temp.Firstname = TestData(intIndex).Firstname
    49.                 temp.Lastname = TestData(intIndex).Lastname
    50.                 temp.PlayerID = TestData(intIndex).PlayerID
    51.                 temp.Weight = TestData(intIndex).Weight
    52.                
    53.                 TestData(intIndex).Firstname = TestData(intIndex + 1).Firstname
    54.                 TestData(intIndex).Lastname = TestData(intIndex + 1).Lastname
    55.                 TestData(intIndex).PlayerID = TestData(intIndex + 1).PlayerID
    56.                 TestData(intIndex).Weight = TestData(intIndex + 1).Weight
    57.                
    58.                 TestData(intIndex + 1).Firstname = temp.Firstname
    59.                 TestData(intIndex + 1).Lastname = temp.Lastname
    60.                 TestData(intIndex + 1).PlayerID = temp.PlayerID
    61.                 TestData(intIndex + 1).Weight = temp.Weight
    62.             End If
    63.         Next
    64.     Loop
    65.    
    66.     For intIndex = 0 To UBound(TestData)
    67.         Debug.Print _
    68.               TestData(intIndex).PlayerID & " " & _
    69.               TestData(intIndex).Firstname & " " & _
    70.               TestData(intIndex).Lastname & " " & _
    71.               TestData(intIndex).Weight
    72.     Next
    73.    
    74. End Sub

  3. #3

    Thread Starter
    New Member
    Join Date
    May 2001
    Posts
    14
    Thanks very much! I'll give it a shot, see how it goes. The only thing I'm wondering about is the performance. This is the slowest type of sort, yes?

  4. #4

  5. #5
    VB6, XHTML & CSS hobbyist Merri's Avatar
    Join Date
    Oct 2002
    Location
    Finland
    Posts
    6,654
    The performance for the above, to my knowledge, gets cumulatively worse for each added item. Here is a solution which requires less calculating with big arrays (but uses more memory too):

    VB Code:
    1. Option Explicit
    2.  
    3. Private Type PlayerArray
    4.     PlayerID As Long
    5.     Firstname As String
    6.     Lastname As String
    7.     Weight As Byte
    8. End Type
    9.  
    10. Dim aPlayer() As PlayerArray
    11. Private Sub SortArray()
    12.     Dim TempArray As New Collection, A As Long, B As Long, C As Long
    13.     Dim SortedArray() As PlayerArray
    14.     TempArray.Add 0
    15.     For A = 1 To UBound(aPlayer)
    16.         For B = 1 To TempArray.Count
    17.             C = CLng(TempArray(B))
    18.             If aPlayer(A).PlayerID < aPlayer(C).PlayerID Then TempArray.Add A, , B: Exit For
    19.         Next B
    20.         'check if we exited from the loop or not
    21.         If B > TempArray.Count Then TempArray.Add A
    22.     Next A
    23.     ReDim SortedArray(UBound(aPlayer))
    24.     For A = 1 To TempArray.Count
    25.         B = CLng(TempArray(A))
    26.         With SortedArray(A - 1)
    27.             .PlayerID = aPlayer(B).PlayerID
    28.             .Firstname = aPlayer(B).Firstname
    29.             .Lastname = aPlayer(B).Lastname
    30.             .Weight = aPlayer(B).Weight
    31.         End With
    32.     Next A
    33.     For A = 0 To UBound(aPlayer)
    34.         aPlayer(A).PlayerID = SortedArray(A).PlayerID
    35.         aPlayer(A).Firstname = SortedArray(A).Firstname
    36.         aPlayer(A).Lastname = SortedArray(A).Lastname
    37.         aPlayer(A).Weight = SortedArray(A).Weight
    38.     Next A
    39. End Sub
    40. Private Sub Form_Load()
    41.     Dim A As Byte
    42.     ReDim aPlayer(2)
    43.     With aPlayer(0)
    44.         .PlayerID = 1
    45.         .Firstname = "Jack"
    46.         .Lastname = "Humblerose"
    47.         .Weight = 80
    48.     End With
    49.     With aPlayer(1)
    50.         .PlayerID = 1
    51.         .Firstname = "Jack"
    52.         .Lastname = "Abrahamson"
    53.         .Weight = 90
    54.     End With
    55.     With aPlayer(2)
    56.         .PlayerID = 0
    57.         .Firstname = "Jack"
    58.         .Lastname = "Rogers"
    59.         .Weight = 100
    60.     End With
    61.     SortArray
    62.     For A = 0 To 2
    63.         With aPlayer(A)
    64.             Debug.Print "PlayerID:  " & .PlayerID
    65.             Debug.Print "Firstname: " & .Firstname
    66.             Debug.Print "Lastname:  " & .Lastname
    67.             Debug.Print "Weight:    " & .Weight
    68.         End With
    69.     Next A
    70. End Sub


    You can get it faster if you can figure out how to use CopyMemory to copy complete data from SortedArray to aPlayer... I tried playing with it, but since I couldn't figure it out in my limited time (have to go to work soon), I didn't do it.

  6. #6
    Frenzied Member
    Join Date
    Aug 2000
    Location
    O!
    Posts
    1,177
    Originally posted by jctsk
    Thanks very much! I'll give it a shot, see how it goes. The only thing I'm wondering about is the performance. This is the slowest type of sort, yes?
    FWIW, you can speed the bubble sort up by coding it in such a way that you only do 1 swap for each pass.
    VB Code:
    1. Dim arry(1 To 3, 1 To 2)
    2. Dim inner    As Integer     ' inner loop index
    3. Dim outer    As Integer     ' outer loop index
    4. Dim lowval   As Integer     ' pointer to low value
    5. Dim swapcol1
    6. Dim swapcol2
    7.  
    8. ' some code to populate the array would go here
    9.  
    10. For outer = LBound(arry) To UBound(arry) - 1
    11.     ' set lowval to current outer row
    12.     lowval = outer                          
    13.     For inner = outer + 1 To UBound(arry)
    14.         ' look for lowest value in remaining rows
    15.         If arry(inner, 1) < arry(lowval, 1) Then lowval = inner
    16.     Next inner
    17.     ' swap row data if a lower value was found
    18.     If lowval <> outer Then
    19.        swapcol1 = arry(outer, 1)
    20.        swapcol2 = arry(outer, 2)
    21.        arry(outer, 1) = arry(lowval, 1)
    22.        arry(outer, 2) = arry(lowval, 2)
    23.        arry(lowval, 1) = swapcol1
    24.        arry(lowval, 2) = swapcol2
    25.     End If
    26. Next outer

  7. #7

    Thread Starter
    New Member
    Join Date
    May 2001
    Posts
    14
    Thanks! I'll give them all a shot, see what will work the best for me.

    Thanks so much for your help

Posting Permissions

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



Click Here to Expand Forum to Full Width