Access - Zahlen aus Zeichenkette extrahieren

Hallo Access Experten,

bei folgender Abfrage Aufgabenstellung bräuchte ich mal Hilfe:
(verwendete Access Version: 2003)

gegeben sind Feldinhalte mit gemischten Zeichen aus Zahlen und Buchstaben.
Zum Beispiel:

Tage/Mo-Sa je 1,5 Std.
Tage/Mo-Sa je 2 Std.
Tage/Mo-Sa je 3 Std.
Tag/Mi 5 Std.
Tag/Do 0,5 Std.
Tag/Fr 0,75 Std.

Aus diesen Zeichenfolgen benötige ich die Stundenanzahl. Also 1,5 ; 2 ; 3 und so weiter.
Die Zeichenketten sind unterschiedlich lang, aber (von rechts nach links betrachtet) beginnt es immer mit dem 6. Zeichen. Wie man oben sieht, benötige ich dann zwischen 1 und 4 Zeichen.

Mit meinen geringen Kenntnissen zu „Right“ und „Len“ komme ich hier nicht weiter.

Für Hilfe schon mal vielen Dank im Voraus.

J.H.

Hallo,

Tage/Mo-Sa je 1,5 Std.
Tage/Mo-Sa je 2 Std.
Tage/Mo-Sa je 3 Std.
Tag/Mi 5 Std.
Tag/Do 0,5 Std.
Tag/Fr 0,75 Std.

benötige ich die Stundenanzahl. Also
1,5 ; 2 ; 3 und so weiter.
Die Zeichenketten sind unterschiedlich lang, aber (von rechts
nach links betrachtet)

beginnt es immer mit dem 6. Zeichen.

??

Wie man oben sieht, benötige ich dann zwischen 1 und 4
Zeichen.

?? Mit anderen Worten, Du benötigst den Stundenwert…

Wenn das oben st. Format des Textes eingehalten wird, dann ging etwa dieses:

Public Function fktRetrieveHours(byVal strText as String) as Double
On error Resume Next
strText= Replace (strText,"Std.","")
strText =Mid(strText,Instrrev(strText," ")+1)
fktRetrieveHours= Str(strText)
End Function

Gruß
Franz,DF6GL

Hallo Franz,

Danke für die schnelle Antwort.

Will das Ganze allerdings in einer Abfrage unterbringen.
Brauche also eine SQL Lösung.

Kannst Du mir auch da helfen?

Viele Grüße

Jorma

Hallo,

Will das Ganze allerdings in einer Abfrage unterbringen.

davon steht in der Ausgangsfrage nichts…

Brauche also eine SQL Lösung.

Eine „reine“ SQL-Lösung (nur mit SQL-Funktionen) gibt es (in Access) nicht. Es müssten trotzdem VBA-Funktionen in einer berechneten Spalte benmüht werden.

Ruf einfach die VBA-Funktion (die in einem Standardmodul stehen muss) in der Abfrage auf…

Gruß
Franz, DF6GL

Hallo Franz,

Die Zeichenketten sind unterschiedlich lang, aber (von rechts
nach links betrachtet)

beginnt es immer mit dem 6. Zeichen.

??

beachte bitte das in Klammern. „Std.“ sind 4 Zeichen plus dem Leerzeichen
davor sinds 5, also ist die letzte Ziffer der Zahl das 6-te Zeichen von rechts.

Wie man oben sieht, benötige ich dann zwischen 1 und 4
Zeichen.

??

„0,75“ sind 4 Zeichen…

Public Function fktRetrieveHours(byVal strText as String) as
Double
On error Resume Next
strText= Replace (strText,„Std.“,"")
strText =Mid(strText,Instrrev(strText," ")+1)
fktRetrieveHours= Str(strText)
End Function

Ich glaube du hast den Code nicht getestet, ich auch nicht, bin zu müd
um die Zeit *gähn*
M.E. fehlt da ein Leerzeichen vor „Std.“ beim Replace(…). Also so:
strText= Replace (strText," Std.","")

Zu prüfen ist m.E. auch was eigentlich rauskommt/geschieht wenn
man den Rückgabewert einer Funktion als Double deklariert sie
aber einen String zurückliefert.

SQL kenn ich mich nich aus.

Guts Restnächtle
Reinhard

Gruß
Franz,DF6GL

Hallo,

Die Zeichenketten sind unterschiedlich lang, aber (von rechts
nach links betrachtet)

beginnt es immer mit dem 6. Zeichen.

??

beachte bitte das in Klammern. „Std.“ sind 4 Zeichen plus dem
Leerzeichen
davor sinds 5, also ist die letzte Ziffer der Zahl das 6-te
Zeichen von rechts.

Ja genau, aber damit BEGINNT nichts , damit hört’s auf… :wink:
Auch wenn die Zeichen von Rechts nach Links gezählt werden, muss die eigentliche Zahl von Links nach Rechts interpretiert werden.

Wie man oben sieht, benötige ich dann zwischen 1 und 4
Zeichen.

??

„0,75“ sind 4 Zeichen…

Ja… Aber wo beginnt die erste Ziffer der Zahl? Die Zahl (Ziffernanzahl) ist zudem jeweils unterschiedlich lang…

KORRIGIERTE FUNKTION:

Public Function fktRetrieveHours(byVal strText as String) as Double
On error Resume Next
strText= Replace (strText," Std.","")
strText =Mid(strText,Instrrev(strText," ")+1)
fktRetrieveHours= strText
End Function

Ich glaube du hast den Code nicht getestet, ich auch nicht,

Stimmt, aber das kann ja der TS übernehmen, was eben einen positiven Lerneffekt hat und der Code an sich besser (oder überhaupt) verstanden wird.

bin zu müd
um die Zeit *gähn*
M.E. fehlt da ein Leerzeichen vor „Std.“ beim Replace(…).
Also so:
strText= Replace (strText," Std.","")

Da hast Du Recht…

Zu prüfen ist m.E. auch was eigentlich rauskommt/geschieht
wenn
man den Rückgabewert einer Funktion als Double deklariert sie
aber einen String zurückliefert.

Weshalb , bzw. wie meinst Du das? Warum sollte sie einen String liefern? Was geschieht ist, dass die Funktion einen Double-Zahlenwert liefert. Wenn Du die Str()- Funktion ansprichst, die vorher im Code war, dann war die hier unzweckmäßig, aber nicht um einen numerischen Wert in einen String zu konvertieren, sondern um das Komma in der extrahierten Ziffernfolge zu einen Dezimalpunkt zu ändern. Eine solche Funktion ist aber hier fehl am Platz , es muss eher eine Typ-Konvertierung von String nach Double passieren, was jetzt durch die interne Typ-Konvertierung bei der Zuweisung der Ziffernfolge an die Funktion von „allein“ passiert.

SQL kenn ich mich nich aus.

Macht gar nichts, hier geht’s um eine VBA-Funktion, die lediglich in einer Abfrage aufgerufen werden kann.

Guts Restnächtle
Reinhard

Gruß
Franz,DF6GL

Hallo Franz,

Ja genau, aber damit BEGINNT nichts , damit hört’s auf… :wink:

Sorry Sir, das ist leider falsch denn natürlich „beginnt“ es da.
Von rechts nach links gesehen beginnt beim 6ten
Zeichen von rechts die Zahl und endet halt x Zeichen
später beim Leerzeichen vor der zahl bzw. eins rechts daneben.

Auch wenn die Zeichen von Rechts nach Links gezählt werden,
muss die eigentliche Zahl von Links nach Rechts interpretiert
werden.

Das stimmt. Das ändert aber rein gar nix dran daß du in deinem
Code von rechts nach links iws „zälhst“
strText =Mid(strText,Instrrev(strText," ")+1)

Ja… Aber wo beginnt die erste Ziffer der Zahl? Die Zahl
(Ziffernanzahl) ist zudem jeweils unterschiedlich lang…

? Bei Mid(strText,Instrrev(strText," ")+1)

Ich glaube du hast den Code nicht getestet, ich auch nicht,

Stimmt, aber das kann ja der TS übernehmen, was eben einen
positiven Lerneffekt hat und der Code an sich besser (oder
überhaupt) verstanden wird.

UP kenn ich inzwischen, was issn nun wieder TS?
Trendsetter? Transsexueller? Tausendsassa? Tiefstapler?

man den Rückgabewert einer Funktion als Double deklariert sie
aber einen String zurückliefert.

Wenn Du die Str()- Funktion
ansprichst, die vorher im Code war, dann war die hier
unzweckmäßig, aber nicht um einen numerischen Wert in einen
String zu konvertieren, sondern um das Komma in der
extrahierten Ziffernfolge zu einen Dezimalpunkt zu ändern.
Eine solche Funktion ist aber hier fehl am Platz , es muss
eher eine Typ-Konvertierung von String nach Double passieren,
was jetzt durch die interne Typ-Konvertierung bei der
Zuweisung der Ziffernfolge an die Funktion von „allein“
passiert.

Ja, Str(…) fand ich zumindest seltsam für den Double-Rückgabewert.
„seltsam“ bedeutet für mich ich muß das testen um genaueres zu sagen.
Naja, heute morgen habe ich deinen ersten Code getestet um zu
schauen wie das mit Str/Double so funktionert.

Naja, getestet mit Excel, prompt kam die Meldung daß Win Excel
beenden muß Im Code fehlte das von mir genannte Leerzeichen,
ich vermute das war der Grund

Zum Komma, ja ich weiß wenn man im Vba-Code Zahlen reinschreibt
muß man den Punkt als Trennzeichen benutzen.
Andererseits „weiß“ Excel-Vba daß 3,14 in einer Zelle eine Zahl ist.
Ohne jedwede Ahnung von Access wirds doch da genauso sein.
Von daher sehe ich erstmal keinen Grund da Komma in Punkt zu
wandeln. „erstmal“=ungetestet.

SQL kenn ich mich nich aus.

Macht gar nichts, hier geht’s um eine VBA-Funktion, die
lediglich in einer Abfrage aufgerufen werden kann.

Aus reiner Neugier, "Abfrage=SQL-Abfrage?
In Zellen von Access kann man deine Funktion nicht anwenden?
So z.B.
In Zelle A1 steht
blabla 1,5 Std.
dann in einer anderen Zelle
=DeineFunktion(A1)
?

Gruß
Reinhard

Hallo,

will diesen Thread nun nicht ellenlang verfolgen…

— es wird nicht „gezählt“ , sondern ein Zeichen (Leerzeichen) (von rechts aus gesehen) „gesucht“ und seine Position (immer von links gesehen) im String ermittelt. Von dieser Position (+1) aus werden alle Zeichen bis zum Ende des Strings ausgeschnitten.

— TS = Thread-Starter == Jorma Heinrichs

— Str() setzt das Komma in einem String, wenn der String als „Zahl“ verwendet werden soll, in einen Punkt um, weil in SQL und in VBA die Dezimal-Trennung nun einmal ein Punkt ist. Das ist hier im Code aber so nicht brauchbar, weil falsch. Wollte dort eher die CDBL()- Konvertierungs-Funktion einsetzen, die aber wegen der angesprochenen internen Konvertierungs-Funktionalität von VBA nicht explizit angegeben zu werden braucht.

— In Access(!) und anderen DB-Systemen ist eine Abfrage ein Objekt, das „Befehle“ enthält und an das Datenbanksystem schickt, um Daten zu liefern oder zu manipulieren. Die Gesamtheit dieser Befehle/Angaben nennt sich SQL. Der „Code“ , der aus diesen Befehlen besteht, läßt sich als SQL-String darstellen. (Select * from Tabelle1 Where ID = 1 Order By xyz)

— Access kennt keine Zellen, nur Felder, und Access ist auch nicht Excel…Da gibt es gewaltige Unterschiede, einer davon ist die genaue Einhaltung/Deklaration/Definiton von Datentypen.

— Die Funktion ist , sofern sie in einem Standardmodul steht, von überall in Access aus aufrufbar, also auch in Text-Feldern (genauer: im Steuerelementinhalt eines Textfeldes).

— und nun isses gut mit diesem Thread…

Hallo Franz,

will diesen Thread nun nicht ellenlang verfolgen…

ich bemüh mich.

— es wird nicht „gezählt“ , sondern ein Zeichen
(Leerzeichen) (von rechts aus gesehen) „gesucht“ und seine
Position (immer von links gesehen) im String ermittelt.

Ich weiß nicht wie Vba intern bei z.B. InstrRev vorgeht. Solange
ich nirgends was offizielles lese gehe ich davon aus daß
wenn z.B. wie hier von rechts ein leerzeichen gesucht wird,
Vba bzw. InstrRev die Textlänge kennt.

In der Tat wird dann von rechts aus nach einem Leerzeichen „gesucht“.
ABER, m.E. wird dabei „gezählt“ wieviele Zeichen kein Leerzeichen
sind. Textlänge minus Zählwert ist dann die Position.
Ja, von links aus gesehen.

— TS = Thread-Starter == Jorma Heinrichs

Aha, kannte ich nicht.

Wollte
dort eher die CDBL()- Konvertierungs-Funktion einsetzen, die
aber wegen der angesprochenen internen

Wenn du nach Deklaration des Rückgabewertes als „as Double“
bei der Wertzuweisung zur Funktion CDbl() benutzt hättest hätte
ich nix gesagt. Du hast aber Str() benutzt.

— und nun isses gut mit diesem Thread…

Okay.

Gruß
Reinhard