03-26-2024, 05:57 PM
(03-26-2024, 05:23 PM)Kernelpanic Wrote: @SMcNeill, why ReDim here? You only use ReDim if you want to change the dimension of an array: from XYZ(12) - ReDim XYZ(15), for example. And it is only applicable to dynamic arrays.
Is this a dynamic array? - I have to check it first, that is a problem of lack of practice.
Where does count come from? Have you tried that? ReDim _Preserve enemy(count): Here the dimension is permanently increased from 1. To see if it works, one would have to try it out in a program.
Code: (Select All)
Type equipment_type 'assign the various types to your TYPE field
name As String
damage As Integer
defense As Integer
durability As Integer
count As Integer
End Type
Dim Shared equipment(20) As equipment_type 'define your variable or array based off that field
Type enemy_type 'the same for the enemies
name As String
damage As Integer
defense As Integer
health As Integer
End Type
Dim Shared enemy(20) As enemy_type 'assign that type to an array, like above
Init_Enemy
Init_Equipment
Sub Init_Enemy
ReDim enemy(200) As enemy_type 'Here is ReDim OK. You have changed the dimension. But why the same type declaration again?
Restore enemy_data 'always use restore to make certain you get the data you want.
Do
Read enemy(count).name, enemy(count).damage, enemy(count).defense, enemy(count).health
If enemy(count).name <> "EOD" Then
count = count + 1
Else
Exit Do
End If
Loop
ReDim _Preserve enemy(count) As enemy_type 'The same
Exit Sub
enemy_data:
Data "Rabbit",2,0,6
Data "Crab",3,1,6
Data "EOD",-1,-1,-1 'end of data fields
End Sub
Sub Init_Equipment
ReDim equipment(200) As equipment_type 'define your variable or array based off that field
Restore equipment_data 'always use restore to make certain you get the data you want.
Do
Read equipment(count).name
Read equipment(count).damage, equipment(count).defense, equipment(count).durability
Read equipment(count).count
If enemy(count).name <> "EOD" Then
count = count + 1
Else
Exit Do
End If
Loop
ReDim _Preserve equipment(count) As equipment_type
Exit Sub
equipment_data:
Data "Bone Spear",2,0,20,0
Data "Flint Spear",4,0,30,0
Data "Copper Spear",6,0,40,0
Data "Iron Spear",8,0,50,0
Data "Stone Axe",1,1,20,0
Data "Copper Axe",3,2,35,0
Data "Iron Axe",4,4,50,0
Data "EOD",-1,-1,-1,-1
End Sub
How did you end up with the code you did? Did you remove the ReDim from what I'd posted? (Compare your DIM SHARED statements to what is in my original post.)
The idea behind this type of data structure is ease of expandability. At the moment, there's only 2 monsters in the game -- rabbits and crabs. I'm certain that number is going to increase in the future. How far is it going to increase??
Who can say at this point in the game development! Maybe 10 monsters. Maybe 32. Maybe 114...
So with this uncertainty in play, we set up our code to do a few basic things:
1) Create an array large enough to hold all those possibiile options.
Code: (Select All)
Sub Init_Enemy
ReDim enemy(200) As enemy_type 'large enough to hold all enemies in one array
Then we run a loop to count and keep track of how many enemies we actually have.
Code: (Select All)
Do
Read enemy(count).name, enemy(count).damage, enemy(count).defense, enemy(count).health
If enemy(count).name <> "EOD" Then
count = count + 1
Else
Exit Do
End If
Loop
The above loads data into our array, starting at element 0, and then increasing the count by 1 for each enemy entry, until it reaches the "End Of Data" field and stops.
3) We then resize that overlarge array down to the point where it *only* holds the data that it needs to.
Code: (Select All)
ReDim _Preserve enemy(count) As enemy_type
In this case, we have 2 valid enemies (which would be in index 0 and 1, respectively) and the "End of Data" entry (which is in index 2). We counted them as we added them in the loop, so this ReDim Preserve trncates the array from 200 elements down to 2 elements, freeing unused memory and keeping our overall footprint as small as possible.
Does it work?
Certainly it does. I use this approach all the time, and there's probably a hundred different examples on the forums here where I've used it in the past. If youu need a testable program for this, here's a very simple one for you:
Code: (Select All)
Screen _NewImage(800, 600, 32)
ReDim num(1000) As Integer
Do
Read num(count)
If num(count) <> -1 Then count = count + 1 Else Exit Do
Loop
ReDim _Preserve num(count) As Integer
Print "There were "; count;
Print "numbers counted and stored in our array (with end of data marker of -1)"
Print "They were:"
Print "(Index)", "(Value)"
For i = 0 To UBound(num)
Print i, num(i)
Next
End
Data 1,2,3,4,5,6,7,8,9,-1
My array starts out insanely large, to make certain it'll hold my data. I then read and count my data. And when that is finished, I simply resize the array to hold *only* the data that it actually needs, while freeing up all that unused space.
It's quick. It's efficient. It's my general goto method for loading data into arrays -- whether it be from DATA statements, or from CSV files or such.