Live-Forum - Die aktuellen Beiträge
Anzeige
Anzeige
HERBERS
Excel-Forum (Archiv)
20+ Jahre Excel-Kompetenz: Von Anwendern, für Anwender

Forumthread: Zweidimensionale Arrays clever vergleichen

Zweidimensionale Arrays clever vergleichen
09.05.2017 13:41:13
Burkhard
Hallo miteinander,
ich habe zwei zweidimensionale Arrays, die ich miteinander vergleichen soll. Dummerweise ist der "Aufbau" unterschiedlich, hier ein Beispiel:
Array1:
User,yes
ProjectUser,maybe
SuperUser,yes
Admin,no
Array2:
Admin,nein
ProjectUser,vielleicht
SuperUser,ja
User,ja
Die Aufgabe besteht darin, herauszufinden, ob die beiden Arrays inhaltlich identisch sind - was für das obige Beispiel zutreffen würde.
Da das Ganze auch noch innerhalb einer Schleife passiert, suche ich nach einer möglichst schnellen Lösung. (Im "wirklichen Leben" sind die Arrays je etwa 100 Zeilen groß.)
WorksheetFunction.Match funktioniert m.W. nur mit eindimensionalen Arrays. Ich habe schon überlegt, ob ich beide Arrays sortieren soll und dann aus den einzelnen Elementen zwei Strings erzeugen (dabei beim zweiten Array "ja" gegen "yes" austauschen etc.), die ich vergleichen könnte. Aber da macht mir der Sort Sorgen ... dann kann ich ja gleich die "klassische" Lösung mit zwei Schleifen nehmen ...
Weiß irgendjemand eine andere clevere Lösung?
Anzeige

12
Beiträge zum Forumthread
Beiträge zu diesem Forumthread

Betreff
Datum
Anwender
Anzeige
AW: Zweidimensionale Arrays clever vergleichen
09.05.2017 13:58:55
yummi
Hallo Burkhard,
so wie deine arrays aufgebaut sind, hast du nur die Möglichkeit mit einem Aufwand von n*n das ganze zu durchsuchen. da Du für jeden Eintrag aus array1 das gesamte array2 bis zur fundstelle durchsuchen musst. Eine schnellere Möglichkeit wäre es, wenn du die Arrays (evtl auch in Hilfsarrays) vorher sortierst und dann vergleichst.
Gruß
yummi
Anzeige
AW: Zweidimensionale Arrays clever vergleichen
09.05.2017 14:04:57
Daniel
Hi
du kannst Application.VLookUp nutzen.
das geht auch mit 2-D-Arrays:
z.b. so
If Array1(1, 2)  Application.VLookUp(Array(1, 1), Array2, 2, 0) Then Msgbox "Abweichung für " & Array(1, 2)
und das mit dem Deutsch-Englisch solltest du ggf vorab in einer Schleife austauschen, damit die Texte gleich sind.
Gruß Daniel
Anzeige
AW: Zweidimensionale Arrays clever vergleichen
09.05.2017 16:28:14
Burkhard
Hi Daniel,
ich bekomme einen Fehler 2042 (nicht gefunden) - ich bin mir aber sicher, dass etwas gefunden werden müsste!
Hier mein Original-Code:
Function AreEntryArraysEqual(arPerm(), arRep()) As Boolean
Dim i As Integer
Dim sPerm As String
Dim sRep As String
Dim var As Variant
AreEntryArraysEqual = True
For i = LBound(arRep) To UBound(arRep)
var = Application.VLookup(arRep(i, 1), arPerm, 2, False)
If IsError(var) Then
GoTo ErrorHandler
Else
sPerm = CStr(var)
End If
sRep = arRep(i, 2)
If Translate(sRep)  sPerm Then
AreEntryArraysEqual = False
Exit For
End If
Next
GoTo CleanUp
ErrorHandler:
DisplayErrorMessage "AreEntryArraysEqual", Err
Err.Clear
CleanUp:
End Function
Was mache ich falsch? arRep(i, 1) kommt in arPerm Spalte 1 (später) vor; arPerm beginnt allerdings mit einem Eintrag, der "" (bzw. 'Leer') enthält.
Grüße
Burkhard
Anzeige
AW: Zweidimensionale Arrays clever vergleichen
10.05.2017 10:28:26
Daniel
Hi
hast du den Spaltenindex richtig gewählt?
ohne die Daten zu kennen, ist es jetzt schwierig
Gruß Daniel
AW: Zweidimensionale Arrays clever vergleichen
10.05.2017 11:39:36
Burkhard
Hallo Daniel,
ich habe mir die beiden Arrays mal ausgeben lassen (das [...] ist von mir, wenn die nächsten Zeilen identisch sind); arRep ist sortiert und ohne Lücken, hat aber einen eigentlich zu hohen UBound; arPerm ist "chaotisch" :
======= arPerm ==========
0: ,
1: ,
2: [...]
8: ,
9: Admin, no
10: P-Admins, yes
11: P-Transaction, no
12: ,
13: ,
14: ,
15: ,
16: P-Data, no
17: ,
18: [...]
23: ,
24: P-User, no
25: ,
26: ,
27: ,
28: ,
29: P-B, no
30: ,
31: [...]
45: ,
46: P-IT_1, no
47: P-IT_2, no
48: ,
49: [...]
65: ,
======= arRep ===========
0: ,
1: Admin, nein
2: P-Admins, ja
3: P-B, nein
4: P-Data, nein
5: P-IT_1, nein
6: P-Transaction, nein
7: P-User, nein
8: ,
9: [...]
36: ,

Der Code, der das erzeugt, sieht so aus (arArray wird so DebugPrintArray arPerm übergeben und ist eben einmal arPerm und einmal arRep)
Sub DebugPrintArray(arArray())
For i = LBound(arArray) To UBound(arArray)
s = CStr(i) & ": " & arArray(i, 1) & ", " & arArray(i, 2)
Debug.Print s
Next
Ich bin mir total unsicher, wann ich hinter dem Array eine Klammer setzen muss und wann nicht. Wenn der Compiler das direkt anmeckert, ist ja gut, aber i.d.R. gibt das ja einen ganz anderen Fehler.
Oder mag das VLookup nicht, dass der erste arPerm-Eintrag leer ist? (Ich bin im Debugger immer gleich auf den zweiten - gültigen - arRep-Eintrag als Suchkriterium gegangen, damit das System nicht nach einem leeren Eintrag sucht, was vermutlich ziemlicher Blödsinn wäre ...)
Grüße
Burkhard
PS: Diese beiden Arrays wären übrigens NICHT identisch ...
Anzeige
AW: Zweidimensionale Arrays clever vergleichen
10.05.2017 11:52:32
Daniel
kannst du die Datei mit den Arrays und dem Code bitte hochladen?
ich bin zu faul, mir deine Einzelinformationen zu einem Ganzen zusammen zu stückeln.
Gruß Daniel
AW: Zweidimensionale Arrays clever vergleichen
10.05.2017 13:23:46
Burkhard
Hallo Daniel,
sorry, aber Hochladen geht leider nicht. Das ist ein Teil von einem ziemlich großen Projekt mit Echtdaten, und wenn ich da mit Anonymisieren anfange, wird's Weihnachten ...
Sag mir, was ich tun kann, um die Einzelinformationen zu ergänzen oder übersichtlicher zu gestalten, das würde ich gerne tun.
Grüße
Burkhard
Anzeige
AW: Zweidimensionale Arrays clever vergleichen
10.05.2017 13:49:21
Daniel
naja, ich müsste jetzt wissen, ob deine Arrays 0 oder 1 basiert sind.
der VLookUp durchsucht die erste Spalte des Arrays, unabhängig davon welche Indexnummer die erste Spalte hat.
ansonsten spricht auch nichts dagegen, wenn du dir die Schleife programmierst.
schleifen mit Arrays sind sehr schnell (im Gegensatz zu schleifen über Zellen)
der VLookUp läuft intern auch mit einer Schleife über die Werte, bis er einen Treffer findet und ist dabei auch nicht viel schneller als eine selbstgeschriebene Schleife.
Gruß Daniel
Anzeige
AW: Zweidimensionale Arrays clever vergleichen
10.05.2017 15:06:53
Burkhard
Hallo Daniel,
ich denke, das ist der entscheidende Hinweis.
Wenn ich arRep(i,0) ohne Laufzeitfehler im Direktbereich abfragen kann, ist arRep wohl zero-based, oder?
(grade verifiziert: mein DebugPrintArray (s.o.) funktioniert auch mit s = CStr(i) & ": " & arArray(i, 0) & ", " & arArray(i, 1) & ", " & arArray(i, 2) - das Array hat also in Wirklichkeit drei Spalten: 0, 1 und 2! Und 0 ist immer leer!)
Da ich die option base Anweisung in dem Modul nicht ändern (bzw. neu einführen) möchte (wer weiß, was dann alles an allen möglichen anderen Stellen nicht mehr passt): kann ich bei der Deklaration bzw. beim reDim des Arrays angeben, dass das Teil one-based sein soll? Oder geht das irgendwie anders?
Grüße
Burkhard
Anzeige
AW: Zweidimensionale Arrays clever vergleichen
10.05.2017 15:30:00
Daniel
HI
Wenn du ein Array dimensionierst, kannst du nicht nur den End- sondern auch den Startwert beliebig und unabhängig von der Option-Base angeben:
(Re)Dim Arr(1 to 100, 1 to 2)
ein nachträgliches Redim Preserve funktioniert nur mit dem UBound (Endwert) der letzten Dimension (Spalte).
dh die erste Spalte bekommst du nachträglich nicht weg. (höchsten durch Umschaufeln per Schleife)
Gruß Daniel
Anzeige
AW: Zweidimensionale Arrays clever vergleichen
10.05.2017 15:43:29
Burkhard
Hurra Hurra!!
Die beiden Arrays waren zero-based, jetzt sind sie one-based.
Das mit den indices beim Redim stand ja in der Hilfe - zweimal geändert, und ES FUNKTIONIERT!!!
LET ME GIVE YOU A BIG HUG FOR THAT 'BASED'-IDEA!
Vielen Dank!
Grüße
Burkhard
AW: Zweidimensionale Arrays clever vergleichen
10.05.2017 13:53:04
Burkhard
Hallo Daniel,
hier nochmal ein Codestück mit Versuchen, die mich auch nicht weitergebracht haben - var ist immer "Fehler 2042", auch bei Count und Match:
Function AreEntryArraysEqual(arPerm(), arRep()) As Boolean
Dim i As Integer
Dim sPerm As String
Dim sRep As String
Dim var0, var1, var2, var3, var4
On Error GoTo ErrorHandler
AreEntryArraysEqual = True
Debug.Print "======= arPerm =========="
DebugPrintArray arPerm
Debug.Print "======= arRep ==========="
DebugPrintArray arRep
For i = LBound(arRep) To UBound(arRep)
sPerm = arPerm(i, 1)
sRep = arRep(i, 1)
If sRep > "" Then
var0 = Application.VLookup(arRep(i, 1), arPerm, 2, False) 'genau, return: Spalte 2
var1 = Application.VLookup(sRep, arPerm, 1, True)     'ungefähr, return: Spalte 1
var2 = Application.CountIf(arPerm, sRep)
var3 = Application.Match(sRep, arPerm, 1)

Grüße
Burkhard
Anzeige
;

Forumthreads zu verwandten Themen

Anzeige
Anzeige
Anzeige
Anzeige
Entdecke relevante Threads

Schau dir verwandte Threads basierend auf dem aktuellen Thema an

Alle relevanten Threads mit Inhaltsvorschau entdecken
Anzeige
Anzeige

Infobox / Tutorial

Zweidimensionale Arrays clever vergleichen


Schritt-für-Schritt-Anleitung

Um zwei zweidimensionale Arrays in Excel VBA clever zu vergleichen, kannst du die folgende Schritt-für-Schritt-Anleitung befolgen:

  1. Arrays deklarieren: Stelle sicher, dass deine Arrays korrekt deklariert sind. Zum Beispiel:

    Dim arPerm(1 To 100, 1 To 2) As Variant
    Dim arRep(1 To 100, 1 To 2) As Variant
  2. Daten befüllen: Fülle die Arrays mit den gewünschten Daten. Hier ein Beispiel mit fiktiven Benutzerdaten:

    arPerm(1, 1) = "User": arPerm(1, 2) = "yes"
    arRep(1, 1) = "User": arRep(1, 2) = "ja"
  3. VBA-Funktion erstellen: Schreibe die Funktion, die die Arrays vergleicht:

    Function AreEntryArraysEqual(arPerm() As Variant, arRep() As Variant) As Boolean
        Dim i As Integer
        Dim var As Variant
        AreEntryArraysEqual = True
    
        For i = LBound(arRep) To UBound(arRep)
            var = Application.VLookup(arRep(i, 1), arPerm, 2, False)
            If IsError(var) Then
                AreEntryArraysEqual = False
                Exit Function
            End If
            If Translate(arRep(i, 2)) <> CStr(var) Then
                AreEntryArraysEqual = False
                Exit Function
            End If
        Next i
    End Function
  4. Fehlerbehandlung: Implementiere eine Fehlerbehandlung, um sicherzustellen, dass die Funktion robust ist.


Häufige Fehler und Lösungen

  • Fehler 2042: Dies geschieht häufig, wenn der gesuchte Wert nicht gefunden wird. Überprüfe, ob der Suchwert korrekt ist und ob dein Array richtig definiert ist (z.B. null- oder einsbasiert).

  • Leere Einträge: Wenn dein Array leere Einträge enthält, kann das zu Problemen führen. Stelle sicher, dass du die leeren Einträge entweder ausschließt oder entsprechend behandelst.

  • Falscher Spaltenindex: Achte darauf, den richtigen Spaltenindex für den VLookup zu verwenden. Der Index ist unabhängig von der Basis (null- oder einsbasiert).


Alternative Methoden

Wenn du mit mehrdimensionalen Arrays in C oder in Swift arbeitest, gibt es verschiedene Ansätze, um Arrays zu vergleichen:

  • Sortieren und Vergleichen: Eine Methode besteht darin, beide Arrays zuerst zu sortieren und anschließend die sortierten Werte zu vergleichen. Dies kann die Effizienz erhöhen, insbesondere bei großen Datenmengen.

  • Hilfsarrays verwenden: Du könntest auch Hilfsarrays einsetzen, um die Daten in einer einheitlichen Struktur zu speichern, bevor du den Vergleich durchführst.


Praktische Beispiele

Hier ist ein praktisches Beispiel, das zeigt, wie du zwei zweidimensionale Arrays vergleichen kannst:

Sub CompareArrays()
    Dim arPerm(1 To 4, 1 To 2) As Variant
    Dim arRep(1 To 4, 1 To 2) As Variant

    ' Beispielwerte
    arPerm(1, 1) = "User": arPerm(1, 2) = "yes"
    arPerm(2, 1) = "Admin": arPerm(2, 2) = "no"
    arRep(1, 1) = "User": arRep(1, 2) = "yes"
    arRep(2, 1) = "Admin": arRep(2, 2) = "nein"

    If AreEntryArraysEqual(arPerm, arRep) Then
        MsgBox "Arrays sind identisch."
    Else
        MsgBox "Arrays sind unterschiedlich."
    End If
End Sub

Tipps für Profis

  • Performance optimieren: Bei der Arbeit mit großen Datenmengen kann das Verwenden von Dictionaries anstelle von Arrays die Performance steigern.

  • Dokumentation: Kommentiere deinen Code gut, um die Nachvollziehbarkeit zu erhöhen, insbesondere bei komplexen Vergleichen.

  • Debugging: Nutze Debug.Print, um Zwischenergebnisse auszugeben. Das hilft, Probleme schnell zu identifizieren.


FAQ: Häufige Fragen

1. Was sind zweidimensionale Arrays in Excel VBA?
Zweidimensionale Arrays sind Datenstrukturen, die Daten in Zeilen und Spalten speichern und häufig zur Organisation von Informationen verwendet werden.

2. Wie kann ich überprüfen, ob zwei Arrays identisch sind?
Du kannst die oben dargestellte Funktion AreEntryArraysEqual verwenden, um zwei zweidimensionale Arrays auf identische Werte zu überprüfen.

3. Gibt es eine maximale Anzahl an Elementen in einem Array?
Ja, die maximale Anzahl hängt von der Excel-Version und der verfügbaren Speicherkapazität deines Systems ab. In der Regel kannst du jedoch bis zu 65.536 Elemente in einem Array speichern.

Beliebteste Forumthreads (12 Monate)

Anzeige
Anzeige
Entdecke mehr
Finde genau, was du suchst

Die erweiterte Suchfunktion hilft dir, gezielt die besten Antworten zu finden

Suche nach den besten Antworten
Unsere beliebtesten Threads

Entdecke unsere meistgeklickten Beiträge in der Google Suche

Top 100 Threads jetzt ansehen
Anzeige