Hier ist eine Funktion, die die Zeile im ListObject (Tabelle) zurückgibt, wo das erste passende Wort gefunden wird.
Public Function MatchFruit(ByVal sInfo As String, ByRef rFruit As Range) As Long
Dim vaSplit As Variant
Dim i As Long, j As Long
Dim rFound As Range
Dim sWhat As String
vaSplit = Split(sInfo, Space(1))
For i = LBound(vaSplit) To UBound(vaSplit)
'strip out non-alpha characters
sWhat = vbNullString
For j = 1 To Len(vaSplit(i))
If Asc(Mid(LCase(vaSplit(i)), j, 1)) >= 97 And Asc(Mid(LCase(vaSplit(i)), j, 1)) <= 122 Then
sWhat = sWhat & Mid(vaSplit(i), j, 1)
End If
Next j
'find the word in the range
Set rFound = Nothing
Set rFound = rFruit.Find(sWhat, , xlValues, xlWhole, , , False)
If Not rFound Is Nothing Then 'if it's found
'return the row in the ListObject
MatchFruit = rFound.Row - rFruit.ListObject.HeaderRowRange.Row
'stop looking
Exit For
End If
Next i
End Function
Angenommen, Ihre erste Tabelle ist tblData und Ihre zweite Tabelle tblFruit genannt, würden Sie die Farbe erhalten mit
=INDEX(tblFruit[Color],MatchFruit([@Info],tblFruit[Fruit]))
und der Preis ähnlich
=INDEX(tblFruit[Price],MatchFruit([@Info],tblFruit[Fruit]))
lange Erklärung
DieDie-Zuweisungszeile verwendet die Split
-Funktion, um eine Zeichenfolge basierend auf einem Begrenzer in ein Array zu konvertieren. Da Ihre Beispieldaten Sätze waren, ist das normale Trennzeichen ein Leerzeichen, um es in Wörter zu teilen. Eine Zeichenfolge wie
This is some line about apples.
in ein Array umgewandelt wird
vaSplit(1) This
vaSplit(2) is
vaSplit(3) some
vaSplit(4) line
vaSplit(5) about
vaSplit(6) apples.
Als nächstes wird die For
Schleife geht in der Anordnung jedes Element durch, um zu sehen, ob es in der anderen Liste nicht finden kann. Die Funktionen LBound
und Ubound
(untere und obere Grenze) werden verwendet, da wir nicht sicher sein können, wie viele Elemente das Array haben wird.
Die erste Operation in der Schleife besteht darin, alle überflüssigen Zeichen zu entfernen. Dazu erstellen wir die Variable sWhat
und setzen sie auf nichts. Dann durchlaufen wir alle Zeichen im Element, um zu sehen, ob sie außerhalb des Bereichs a...z
liegen. Im Grunde wird alles, was ein Buchstabe ist, an sWhat
angehängt und alles was nicht ist (eine Zahl, ein Leerzeichen, ein Punkt) tut es nicht. Am Ende sWhat
ist das gleiche wie das aktuelle Element mit allen Nicht-Alpha-Zeichen entfernt. In diesem Beispiel würden wir wegen des Zeitraums nie übereinstimmen, also ist es abgestreift.
Sobald wir eine gute sWhat
haben, verwenden wir jetzt die Find
Methode, um zu sehen, ob dieses Wort im rFruit
Bereich existiert. Wenn dies der Fall ist, wird rFound
nicht Nothing
sein und wir gehen voran.
Beachten Sie, dass rFound
ist und die Funktion null zurückgibt, wenn es das Wort in dem Bereich nicht findet.
Wenn das Wort gefunden wird, gibt die Funktion die Zeile zurück, in der sie gefunden wurde, in der Zeile, in der ListObject
beginnt. Auf diese Weise gibt die Funktion die Zeile mit den Daten des ListObject
nicht auf dem Arbeitsblatt zurück. Dies ist nützlich, wenn Sie in eine INDEX
Formel einbeziehen. Um einer Formel etwas zurückzugeben, weisen Sie dem Namen der Formel etwas zu.
Schließlich hört die Exit For
Zeile einfach auf, durch das Array zu suchen, sobald eine Übereinstimmung gefunden wurde. Wenn Ihre Daten mehr als eine Übereinstimmung aufweisen, wird nur die erste zurückgegeben.
Fehlerbehebung
Der wahrscheinlichste Fehler, die Sie finden, ist, dass die Funktion Null zurück, wenn Sie es erwarten eine Zeilennummer zurück. Das bedeutet höchstwahrscheinlich, dass es keine Wörter in der Liste gefunden hat.
Wenn Sie sicher sind, dass beide Listen ein passendes Wort enthalten, gehen Sie folgendermaßen vor: Geben Sie nach der Set rFound =
Zeile eine Debug.Print
Anweisung ein.
Set rFound = rFruit.Find(sWhat, , xlValues, xlWhole, , , False)
Debug.Print "." & sWhat & "."
If Not rFound Is Nothing Then 'if it's found
Die sWhat
zu dem Direkt-Fenstern (Strg + G im VBE die Direkt-Fenster zu sehen) gedruckt wird. Die Perioden um das Wort sind so, dass Sie nicht druckbare Zeichen (wie Leerzeichen) sehen können. Wenn Sie versuchen, .pears .
mit pears
in Übereinstimmung zu bringen, wird es nicht passen, weil das erste ein Leerzeichen am Ende hat - und Sie können das sehen, weil wir Perioden vorher und nachher feststeckten. Wenn Leerzeichen ein Problem darstellen, können Sie die Trim$()
Funktion auf sWhat
zuerst loswerden.
Mit dieser Debug.Print
Aussage, könnten Sie Ergebnisse sehen wie
.paers.
in diesem Fall würde erkennen, dass Sie einen Tippfehler haben.
Nur ein kleiner Hinweis -> warum versuchst du es nicht ein bisschen einfacher zu machen und es dann komplizierter zu machen? Z.B. für "Äpfel" statt "Dies ist eine Zeile über Äpfel". Dort können Sie leicht einen Index (Match; Match) verwenden. – Vityata
Danke für Ihren Kommentar. Ich stimme deinem Standpunkt zu. Aber dieses Beispiel war nur eine vereinfachte Version eines komplizierteren Blattes. Das Originalblatt enthält viel mehr Zeilen und der Wert in der Spalte "info" ist viel komplizierter. Eine Substitution dieser Werte ist also keine Option. EDIT: Nebenbei, diese Werte mit VBA ersetzen würde erfordern ein ähnliches Skript. ;) –