Archief - [PROG][VB/VBA] Probleem met "ReDim" voor matrices

Het archief is een bevroren moment uit een vorige versie van dit forum, met andere regels en andere bazen. Deze posts weerspiegelen op geen enkele manier onze huidige ideeën, waarden of wereldbeelden en zijn op sommige plaatsen gecensureerd wegens ontoelaatbaar. Veel zijn in een andere tijdsgeest gemaakt, al dan niet ironisch - zoals in het ironische subforum Off-Topic - en zouden op dit moment niet meer gepost (mogen) worden. Toch bieden we dit archief nog graag aan als informatiedatabank en naslagwerk. Lees er hier meer over of start een gesprek met anderen.

nickman

Legacy Member
Hey,
Ik heb het volgende stukje code:
Code:
'Klasse om het controleren op dubbele boeking makkelijker te maken
Private profTable As New HashTable
Private profMatrix()        'Een matrix die alle proffen bevat
Private overlapMatrix()        'Een matrix die alle overlappingen per prof bevat

Public Sub initRoosterCheck()
    profTable.SetSize (10000)
    Dim profMatrix()
    Dim overlapMatrix()
    
    ReDim Preserve profMatrix(2, 40)
    ReDim Preserve overlapMatrix(2, 40)
    
    ReDim Preserve profMatrix(3, 40)
    ReDim Preserve overlapMatrix(3, 40)
End Sub
Alles gaat goed tot aan de eerste twee ReDim statements, maar wanneer ik aan die ReDim naar (3, 40) kom dan krijg ik volgende fout melding:

Het subscript valt buiten het bereik (Fout 9)

Ik snap niet waarom ik dit krijg aangezien dit toch net de bedoeling van ReDim is? Om dynamische arrays te maken?

Greetz!

daVinci

Legacy Member
Met een redim Preserve statement kan je alleen de laatste dimensie van je array veranderen. Terwijl jij de eerste dimensie wil veranderen. Dit komt uit de helpfile:

Met het sleutelwoord Preserve kunt u alleen de laatste matrixdimensie wijzigen. U kunt het aantal dimensies in het geheel niet wijzigen. Als de matrix bijvoorbeeld slechts één dimensie heeft, kunt u de grootte van deze dimensie aanpassen omdat dit de laatste en enige dimensie is. Als de matrix echter twee of meer dimensies heeft, kunt u alleen de grootte van de laatste dimensie wijzigen en toch de inhoud van de matrix behouden. Het volgende voorbeeld geeft aan u hoe de grootte van de laatste dimensie van een dynamische matrix kunt wijzigen zonder bestaande gegevens te verwijderen die in de matrix zijn opgenomen.

ReDim X(10, 10, 10)
. . .
ReDim Preserve X(10, 10, 15)

Op dezelfde manier kunt u bij het gebruik van Preserve de omvang van de matrix wijzigen door alleen de bovenste grens te wijzigen; het wijzigen van de onderste grens veroorzaakt een fout.

nickman

Legacy Member
Hmmmm, da's wel kut want dat is net wat ik nodig had, de eerste dimentie veranderen...
In VB kan je zeker geen Array van een Array maken?
Of moet ik dan gewoon even een simpele klasse hiervoor maken? om dan iets als
Code:
Dim ProfMatrix() As MyArray
te doen?

En anders moet ik mijn matrix maar "groot genoeg" nemen zeker?

R3Deye

Legacy Member
nickman zei:
En anders moet ik mijn matrix maar "groot genoeg" nemen zeker?

Zou ik afraden, 1 is niet echt zuinig, 2 je hebt een limiet.
Andere optie is je kan heel de data gaan kopieren in een temp array, de originele vergroten zonder preserve, en dan data terug kopieren, persoonlijk vind ik dat ook wat overbodig.

Een andere manier om rond dit probleem te gaan is gebruik maken van een UDT (user defined type)
voorbeeld:
Code:
Option Explicit
Option Base 0

Private Type tARRAY
    a(40) As String    ' weet niet welke variable type je gebruik, verander naar keuze
End Type

Private profMatrix() As tARRAY
Private overlapMatrix() As tARRAY

Private Sub Form_Load()

    ReDim profMatrix(0 To 1) As tARRAY
    ReDim overlapMatrix(0 To 1) As tARRAY
    
    ' voor debug
    profMatrix(0).a(15) = "1234"
    overlapMatrix(1).a(34) = "abcd"
    
    ' vergroot bereik met behoud van data
    ReDim Preserve profMatrix(0 To 2) As tARRAY
    ReDim Preserve overlapMatrix(0 To 2) As tARRAY

    ' debug
    MsgBox profMatrix(0).a(15)      ' geeft 1234
    MsgBox overlapMatrix(1).a(34)   ' geeft abcd

End Sub

EDIT;
Was me aan het vervelen, hier is een voorbeeld met een dynamische array in de UDT die je kan vergroten indien nodig.
Code:
Option Explicit
Option Base 0

Private Type tARRAY
    a() As String       ' variable type ?
End Type

Private profMatrix() As tARRAY
Private overlapMatrix() As tARRAY

Private Sub Form_Load()

    ' maak 2/40
    INIT_Matrix profMatrix, 2, 40
    INIT_Matrix overlapMatrix, 2, 40
    
    ' voor debug
    profMatrix(0).a(15) = "1234"
    overlapMatrix(1).a(34) = "abcd"
    
    ' vergroot 1ste bereik met behoud van data, word 10/40
    EXT_Matrix_1D profMatrix, 10
    EXT_Matrix_1D overlapMatrix, 10

    ' vergroot 2de bereik met behoud van data, word 10/80
    EXT_Matrix_2D profMatrix, 80
    EXT_Matrix_2D overlapMatrix, 80
    
    ' debug
    MsgBox profMatrix(0).a(15)      ' geeft 1234
    MsgBox overlapMatrix(1).a(34)   ' geeft abcd

End Sub

Private Sub INIT_Matrix(ByRef M() As tARRAY, lR1 As Long, lR2 As Long)
    ReDim M(0 To lR1 - 1)
    Dim l As Long
    For l = 0 To (lR1 - 1)
        ReDim M(l).a(0 To lR2 - 1)
    Next l
End Sub

Private Sub EXT_Matrix_1D(ByRef M() As tARRAY, lR1 As Long)
    ReDim Preserve M(0 To lR1 - 1)
End Sub

Private Sub EXT_Matrix_2D(ByRef M() As tARRAY, lR2 As Long)
    Dim l As Long
    For l = 0 To UBound(M)
        ReDim Preserve M(l).a(0 To lR2 - 1)
    Next l
End Sub

nickman

Legacy Member
Ja, ik weet zeker dat een matrix "groot" genoeg kiezen helemaal nergens op slaagt, maar voor dit doel maakt het ni zo heel veel uit eigenlijk ;).

En de oplossing die jij suggereerde heb ik ook aangehaald in mijn tweede reply, en is dus idd de beste oplossing ;).

Als VB nu maar gelinkte lijsten of dergelijke had he... :D
Het archief is een bevroren moment uit een vorige versie van dit forum, met andere regels en andere bazen. Deze posts weerspiegelen op geen enkele manier onze huidige ideeën, waarden of wereldbeelden en zijn op sommige plaatsen gecensureerd wegens ontoelaatbaar. Veel zijn in een andere tijdsgeest gemaakt, al dan niet ironisch - zoals in het ironische subforum Off-Topic - en zouden op dit moment niet meer gepost (mogen) worden. Toch bieden we dit archief nog graag aan als informatiedatabank en naslagwerk. Lees er hier meer over of start een gesprek met anderen.
Terug
Bovenaan