Anzeige
Anzeige
HERBERS
Excel-Forum (Archiv)
20+ Jahre Excel-Kompetenz: Von Anwendern, für Anwender

Forumthread: Feststellen ob Array dimensioniert ist

Feststellen ob Array dimensioniert ist
19.03.2015 10:17:12
Heiko
Hallo VBA Experten,
Ich hab einen Codeschnipsel, mit dem ich prüfe, ob ein Array bereits dimensioniert ist oder ob es richtig dimensioniert ist. In beiden Fällen dimensioniere ich es neu und fülle es mit Daten.
Das Ganze mache ich mehrmals für verschieden Arrays.
Meine Frage ist nun, wie ich den Code evtl. vereinfachen bzw. verallgemeinern kann.
- Leider kann die Abfrage ob das Array dimensioniert ist oder ob es die richtige Größe hat nicht mit OR in der selben Zeile stehen.
- Die Redimensioniereung kann ich auch nicht außerhalb der If Anweisung schreiben, weil sonst immer befüllt wird, auch wenn das Array dimensioniert ist und die richtige Größe hat.
- In eine neue Sub auslagern hat nicht hingehauen, weil es mir nicht gelungen ist, den Blattname (hier: "fit") und die verschiedenen Spalten, wo die Daten stehen, zu übergeben...
Kann jemand mal reinsehen? Bin für Ideen dankbar...
'***** X Werte *****
If (0 / 1) + (Not Not aX) = 0 Then
ReDim aX(nSteps)
tmpX = fit.Range("A1:A" & nSteps & "").Value
For lRow = 1 To UBound(tmpX)
If Not IsEmpty(tmpX(lRow, 1)) Then aX(lRow) = tmpX(lRow, 1)
Next lRow
ElseIf UBound(aX())  nSteps Then
ReDim aX(nSteps)
tmpX = fit.Range("A1:A" & nSteps & "").Value
For lRow = 1 To UBound(tmpX)
If Not IsEmpty(tmpX(lRow, 1)) Then aX(lRow) = tmpX(lRow, 1)
Next lRow
End If

'***** Y Werte *****
If (0 / 1) + (Not Not aYObs) = 0 Then ' Abfrage fuer dimension. Array kann nicht in der selben  _
Zeile stehen wegen IndexFehler, daher Code doppelt!
ReDim aYObs(nSteps)
tmpYObs = fit.Range("B1:B" & nSteps & "").Value
For lRow = 1 To UBound(tmpYObs)
If Not IsEmpty(tmpYObs(lRow, 1)) Then aYObs(lRow) = tmpYObs(lRow, 1)
Next lRow
ElseIf UBound(aYObs())  nSteps Then
ReDim aYObs(nSteps)
tmpYObs = fit.Range("B1:B" & nSteps & "").Value
For lRow = 1 To UBound(tmpYObs)
If Not IsEmpty(tmpYObs(lRow, 1)) Then aYObs(lRow) = tmpYObs(lRow, 1)
Next lRow
End If

'***** Background Werte *****
If (0 / 1) + (Not Not aBg) = 0 Then
ReDim aBg(nSteps)
tmpBG = fit.Range("J1:J" & nSteps & "").Value
For lRow = 1 To UBound(tmpBG)
If Not IsEmpty(tmpBG(lRow, 1)) Then aBg(lRow) = tmpBG(lRow, 1)
Next lRow
ElseIf UBound(aBg())  nSteps Then
ReDim aBg(nSteps)
tmpBG = fit.Range("J1:J" & nSteps & "").Value
For lRow = 1 To UBound(tmpBG)
If Not IsEmpty(tmpBG(lRow, 1)) Then aBg(lRow) = tmpBG(lRow, 1)
Next lRow
End If
Das Ganze klappt zwar sehr gut, aber es kommt mir einfach umständlich und zu lang vor. Die Redimensionierung und Befüllung steht hier für 3 Arrays ganze 6 mal...
Heiko

Anzeige

7
Beiträge zum Forumthread
Beiträge zu diesem Forumthread

Betreff
Datum
Anwender
Anzeige
Ziemlich merkwürdig das Ganze, habe ich so ...
19.03.2015 12:30:16
Luc:-?
…noch nie gesehen, Heiko;
was soll den das sein: If (0 / 1) + (Not Not aX) = 0 Then? Sehr seltsam!
Man könnte ja denken, dass die Arrays irgendwo schon vordimensioniert wurden, weil das hier fehlt, bspw als Dim aX As Variant oder nur Dim aX, ohne bzw mit leerem Klammerpaar nach dem VariablenNamen. Ohne () kann man auf jeden Fall auch IsEmpty(aX) oder IsArray(aX) fragen. Ggf handelt es sich aber auch um ein sog ParamArray, dann ist UBound(aX) = -1 im LeerFall, also < LBound(aX).
Warum sollte (0 / 1) + etwas anderes ergeben als 0 / 1 + oder gleich 0 +?
Natürlich kann man beides nur mit Or verbinden, wenn die 1.Bedingung fragt, ob es sich um einen leeren Variant handelt, weil in diesem Fall die 2.Bedingung nicht mehr abgefragt wird. Aber das wird hier ja nicht gemacht! Wenn das Array nicht Variant ist u/o ursprünglich mit Leerklammern dimensioniert wurde, kann man zuerst auch IsError(aX(0)) fragen, wenn zuvor On Error Resume Next geschrieben wurde (kann danach wieder auf On Error GoTo … gesetzt wdn).
Wirklich sehr merkwürdig…!
Gruß, Luc :-?
Besser informiert mit …

Anzeige
AW: Feststellen ob Array dimensioniert ist
19.03.2015 16:15:58
Namenloser
Hallo
wenn ich jetzt nix übersehe dann ist doch die Redimensionierung und Befüllung der Arrays im if und else Teil gleich. Daher ist doch die Prüfung ob ein Array existiert oden ob es schon dimensioniert wurde unnötig. Im If (0 / 1) + (Not Not aYObs) = 0 Then versteh ich ja noch das (Not Not aYObs), aber was bezweckst du mit (0 / 1) + ?
hier mal n luftcode-bsp wie du das ganze mit einer Sub erledigen könntest:
Sub RedimMyArr(ByRef vArr, nSteps As Long, sCol As String, sTbl As String)
Dim c, i As Long
ReDim vArr(nSteps)
c = ActiveWorkbook.Worksheets(sTbl).Cells(1, sCol).Column
For i = 1 To nSteps
vArr(i) = ActiveWorkbook.Worksheets(sTbl).Cells(i, c)
Next
End Sub
Der aufruf wäre dann entsprechend:

dim aX()
dim aYObs()
RedimMyArr aX, 10, "A", "fit"
RedimMyArr aYObs, 10, "B", "fit"

Anzeige
AW: Feststellen ob Array dimensioniert ist
20.03.2015 12:02:22
Heiko
hi Namenloser, hi Luc,
vielen Dank für Eure Beiträge!
Die Abfrage, ob ein Array richtig dimensioniert bzw. gefüllt ist, erübrigt sich leider nicht, weil ich ja auch den Fall haben kann, wo alles ok ist.
1) Alles ok, Array richtig dimensioniert und gefüllt: keine Aktion
2) Array zwar gefüllt, aber nicht in der richtigen Größe: Array neu dimensionieren
3) Array dimensioniert, aber leer: Wie 2.
- Leider kann 2 und 3 nicht mit OR in der selben Zeile stehen, weil ein leeres Array mit UBound() einen Indexfehler ergibt.
- Die Abfrage (Not Not arr) alleine ergibt seltsamerweise genau wie 0 + (Not Not arr) einen Fehler "Ausdruck zu komplex".
Geht also leider nur mit der super seltsamen obermerkwürdigen Formulierung (0/1) + (Not Not arr).
Namenloser, mit Deinem Tip konnte ichs deutlich verkürzen (danke!), leider muss ich immer noch erst abfragen, ob das array leer ist bevor ich die Größe feststellen kann. Daher ist immer noch If, Elseif mit 2 mal derselben Redim Anweisung nötig...
Danke schön, Heiko

Anzeige
Viell. solltest du meinen BT nochmals lesen, ...
20.03.2015 18:03:15
Luc:-?
…Heiko,
und zwar aufmerksamer…!
Luc :-?

AW: Feststellen ob Array dimensioniert ist
21.03.2015 05:54:42
Luschi
Hallo Heike,
ich mach das immer so:

Sub testArrayDim()
Dim myArr As Variant, ok As Boolean
MsgBox VarType(myArr)
ReDim myArr(3, 2)
If VarType(myArr) = 8204 Then   '8192 (Datenfeld) + 12 (Variant)
MsgBox "Das Array 'myArr' ist dimensioniert!"
If UBound(myArr, 1) = 3 And UBound(myArr, 2) = 2 Then
ok = True
End If
MsgBox "Array 'myArr' ist " & IIf(Not ok, "nicht ", "") & "richtig dimensioniert!"
Else
MsgBox "Die Variable myArr' ist kein Array!"
End If
End Sub
Gruß von Luschi
aus klein-Paris

Anzeige
-o, Luschi, nicht -e! ;-] Gruß owT
21.03.2015 13:47:39
Luc:-?
:-?

;
Anzeige
Anzeige

Infobox / Tutorial

Feststellen, ob ein Array in VBA dimensioniert ist


Schritt-für-Schritt-Anleitung

  1. Erstelle eine Subroutine: Beginne mit der Erstellung einer Subroutine, die die Array-Dimensionierung überprüft und das Array bei Bedarf neu dimensioniert.

    Sub RedimMyArr(ByRef vArr, nSteps As Long, sCol As String, sTbl As String)
        Dim c As Long, i As Long
        ReDim vArr(nSteps)
        c = ActiveWorkbook.Worksheets(sTbl).Cells(1, sCol).Column
        For i = 1 To nSteps
            vArr(i) = ActiveWorkbook.Worksheets(sTbl).Cells(i, c)
        Next
    End Sub
  2. Rufe die Subroutine auf: Definiere deine Arrays und rufe die Subroutine für jedes Array auf.

    Dim aX() As Variant
    Dim aYObs() As Variant
    RedimMyArr aX, 10, "A", "fit"
    RedimMyArr aYObs, 10, "B", "fit"
  3. Überprüfe die Dimensionierung: Füge Logik hinzu, um sicherzustellen, dass das Array nur dann neu dimensioniert wird, wenn es leer oder nicht in der richtigen Größe ist.


Häufige Fehler und Lösungen

  • Fehler bei der Dimensionierung: Wenn du versuchst, UBound() auf ein nicht dimensioniertes Array anzuwenden, erhältst du einen Indexfehler. Stelle sicher, dass das Array vor der Verwendung dimensioniert wird.

  • Komplexe Ausdrücke: Der Ausdruck If (0 / 1) + (Not Not aX) = 0 Then kann verwirrend sein. Verwende stattdessen einfach If IsEmpty(aX) Then oder If Not IsArray(aX) Then.


Alternative Methoden

  • Verwendung von VarType: Du kannst VarType verwenden, um zu überprüfen, ob eine Variable ein Array ist. Ein Beispiel:

    If VarType(myArr) = vbVariant Then
        MsgBox "Das Array 'myArr' ist dimensioniert!"
    End If
  • Error Handling: Nutze On Error Resume Next und On Error GoTo 0, um Fehler bei der Abfrage von Array-Indizes zu behandeln.


Praktische Beispiele

Hier ist ein Beispiel, das die Funktionsweise von Arrays in VBA demonstriert:

Sub testArrayDim()
    Dim myArr As Variant
    ReDim myArr(3, 2)

    If VarType(myArr) = 8204 Then
        MsgBox "Das Array 'myArr' ist dimensioniert!"
    End If

    If UBound(myArr, 1) = 3 And UBound(myArr, 2) = 2 Then
        MsgBox "Array 'myArr' ist richtig dimensioniert!"
    End If
End Sub

Tipps für Profis

  • Verwende Parameter: Nutze Parameter in Subroutinen, um die Flexibilität deiner Code-Struktur zu erhöhen. So kannst du Arrays dynamisch anpassen, ohne redundanten Code zu schreiben.

  • Fehlerbehandlung implementieren: Baue eine robuste Fehlerbehandlung ein, um den Code stabiler zu machen, insbesondere wenn du mit Arrays arbeitest.


FAQ: Häufige Fragen

1. Wie überprüfe ich, ob ein Array dimensioniert ist?
Verwende IsArray(myArray) in einer If-Abfrage, um zu prüfen, ob die Variable ein Array ist.

2. Was mache ich, wenn ich einen Indexfehler bekomme?
Stelle sicher, dass das Array dimensioniert ist, bevor du auf Elemente zugreifst. Verwende Error Handling, um Indexfehler abzufangen.

3. Kann ich Arrays in einer Funktion zurückgeben?
Ja, du kannst ein Array aus einer Funktion zurückgeben, indem du es als Variant deklarierst und es dann entsprechend zurückgibst.

Beliebteste Forumthreads (12 Monate)

Anzeige
Anzeige
Anzeige