Hallo,
aus unserem ERP System kann ich mir eine *.csv Datei erstellen. Diese kann ich dann als *.txt Datei ablegen.
In der ersten Spalte stehen 7 stellige Codenummern, in der zweiten Spalte ein Text.
Ich möchte nun die erste Spalte nach unten durchsuchen nach einer Zeichenfolge, die ich mit UINumEntry vorgebe.
Wenn ich eine Übereinstimmung gefunden habe, soll der Text aus der zweiten Spalte in einen string geschrieben werden.
Hat zufällig jemand so etwas schon einmal gemacht, oder kann mir einen Tipp geben ?
-
-
zufällig jemand so etwas schon einmal gemacht
Nicht nur zufälligCode
Alles anzeigenCONST string dateiname:="HOME:unterordner/datei.txt"; VAR iodev dateihandle; VAR string dummystring; VAR string suchstring; Open dateiname,dateihandle\Read;
Jetzt ist die Datei zum Lesen offen.
Dann zeilenweise einlesen, erst die erste Zeile:
In der ersten Zeile ist entweder schon EOF (EndOfFile) oder nicht, EOF ist vordefiniert und kann mit beliebigen Textdateien so benutzt werden:Codedummystring:=ReadStr(dateihandle); WHILE (NOT (dummystring="EOF")) DO !....hier die Datenverarbeitung angewendet auf "dummystring" (s.U.) !Danach: !Neue Zeile einlesen mit ReadStr, Zähler springt automatisch eine Zeile weiter: dummystring:=ReadStr(dateihandle); ENDWHILE close dateihandle;
Close am Ende nicht vergessen, auch in Fehlerfällen.
Innerhalb der Schleife hast Du in jedem Durchgang einmal den Inhalt der jeweiligen Zeile in "dummystring". Den musst Du dann vernünftig durchsuchen:CodeIF StrLen(dummystring)>1 then IF ((strMatch(dummystring,1,suchstring))<=strLen(dummystring)) .... Hier wurde der Suchbegriff gefunden. endif endif
Mit StrPart kannst Du nun die Zeile splitten und den relevanten Teil wegspeichern (Ich würde die Ausgabe erst nach Beendigung der Schleife machen.) Mit ValToStr kannst Du die evtl. numerische Eingabe in einen Suchstring umwandeln.Grüße,
Michael -
Hallo,
wenn Du die Datei Zeilenweise ausliest, musst Du beachten, dass ein String nur 80 Zeichen lang sein kann und Du zum Einlesen längerer Zeilen den Zeilenrest erst im nächsten Lesevorgang erhältst.
CSV-Dateien haben in der Regel ein Trennzeichen (z.B. ";"). Die Instruktion "ReadStr" kann aber auch so verwendet werden, dass jeweils nur die nächste Spalte ausgelesen wird, also bis zum Trennzeichen.
Dies wird wie folgt programmiert:Gruß
Micky -
Entschuldigung, dass ich mich erst jetzt zurück melde.
Ich habe es nun wie folgt gelöst.Code
Alles anzeigenPROC ReadTextFile() !Dieser Wert wird über UiNumEntry eingegeben CONST string stSucheNach:="2256002"; VAR iodev dateihandle; !VAR string suchstring; VAR num i2; VAR num n; TPErase; !Für Testzwecke string löschen FOR i FROM 1 TO Dim(stMyErgebnis,1) DO stMyErgebnis{i}:=""; ENDFOR !String vor dem neuen lesen löschen n:=1; FOR i FROM 1 TO Dim(stRead,2) DO FOR i2 FROM 1 TO 2 DO stRead{i2,n}:=""; ENDFOR IF stRead{1,i}<>EOF Incr n; ENDFOR !Kanal schließen Close dateihandle; !Kanal öffnen Open "HOME:/Mappe2.csv", dateihandle\Read; !*.csv komplett Datei lesen n:=1; FOR i FROM 1 TO Dim(stRead,2) DO FOR i2 FROM 1 TO 2 DO stRead{i2,n}:=ReadStr(dateihandle\Delim:=";"\DiscardHeaders); ENDFOR IF stRead{1,i}<>EOF Incr n; ENDFOR !Text suchen in gelesener Datei FOR i FROM 1 TO Dim(stRead,2) DO IF stRead{1,i}=stSucheNach THEN stMyErgebnis{1}:=stRead{1,i}; stMyErgebnis{2}:=stRead{2,i}; ENDIF ENDFOR !Kanal schließen close dateihandle; !Fehlerbehandlung IF stMyErgebnis{1}="" AND stMyErgebnis{2}="" THEN TPErase; TPWrite"Fehler Artikelnummer"; Stop; ELSE FOR i FROM 1 TO Dim(stMyErgebnis,1) DO TPWrite stMyErgebnis{i}; ENDFOR ENDIF ENDPROC
-
Geht das mit \Delim:=";" ?
Ich dachte immer daß Delimiters im ASCII-Code geschrieben werden müssen. -
Ich habe so im RSO probiert. Und es hat funktioniert.
-
Hallo,
es gibt einen Unterschied beim Einlesen von Daten zwischen dem realen und dem virtuellen Controller
Beim realen Controller mussten wir die folgende Zeile zum Einlesen verwenden
und beim virtuellen die folgende.
da der Zeilenumbruch unterschiedlich behandelt wird.
Eventuell hast Du beim lesen bis zum nächsten Delimiter kein Problem, aber ich würde es auf jeden Fall nochmal am realen Controller testen.
Gruß
Micky -
Ich häng mich mal hier dran....
kämpfe auch mit der Begrenzung String Zeichelänge maximal 80
Ich möchte ein Modul lesen mit einen Arry von Robtargets, doch die 80 zeichen reichen ja nichtmal für ein einzelnes Robtarget
das einlesen wollte ich jetzt stoppen bei "],["
trage ich das so in ReadStr(logfile\Delim:="],[" ein wird jedes Komma als Zeilentrennung interpretiert, auch ohne die Klammern
auch das ganze als ASCII Hex ReadStr(logfile\Delim:="\5d"+"\2c"+"\5b"); gibt das gleiche Ergebniss
wo liegt mein "Denk"Fehler?
-
Hallo Zusammen,
ich hab mal eine .csv Datei in einen String Array eingelesen , natürlich kommt es bei Überschreitung der max.Zeichenlänge zum Zeilenumbruch.
In deinem Fall mit robtarget
Erste Zeile Stringlänge mit StrLen die Länge des Strings ermitteln , dann mit StrMatch nach ]] suchen , gefunden robtarget komplett
Hab dann angefangen den String zu zerlegen zb. mit StrMatch nach [[ oder ],[ suchen dann mit StrPart string vor und nach dem Suchergebis zwischenspeichern
Immer wieder die Stringlänge von der zweiten Zeile ermittelt und dort mit StrMatch nach ]] oder suchen. Ist die Gesamtstringlänge kleiner 80 Zeichen
den String speichern . Igendwann hat man einen Array von Teilstrings die den Inhalt der robtarget ergibt .
Hab dann aus diesen Teilstrings ein Programmmodul erstellt.Die Konvertierung hab ich im Task 2 abgearbeitet das Modul ins Home Verzeichnis geladen.Task 1 hats geladenund abgearbeitet. Was einfacheres ist mir nicht eingefallen. Viel Spass beim konvertieren
LG Bernhard
-
Ich häng mich mal hier dran....
kämpfe auch mit der Begrenzung String Zeichelänge maximal 80
Ich möchte ein Modul lesen mit einen Arry von Robtargets, doch die 80 zeichen reichen ja nichtmal für ein einzelnes Robtarget
das einlesen wollte ich jetzt stoppen bei "],["
trage ich das so in ReadStr(logfile\Delim:="],[" ein wird jedes Komma als Zeilentrennung interpretiert, auch ohne die Klammern
auch das ganze als ASCII Hex ReadStr(logfile\Delim:="\5d"+"\2c"+"\5b"); gibt das gleiche Ergebniss
wo liegt mein "Denk"Fehler?
Ich hatte vor einiger Zeit ein ähnliches Problem und mich dann dazu entschlossen das ganze über RawBytes zu machen um diese Beschränkung zu umgehen und etwas zu haben was möglichst vielseitig einsetzbar ist. Inwieweit mir das gelang, bleibt abzuwarten
Hier mal ein Beispielcode. Ich habe hier einen Record für meinen speziellen Fall benutzt aber das kann man ja beliebig umstricken.
Vielleicht hilft es ja schon alleine als Denkanstoß
Code
Alles anzeigenFUNC result TransRecord(VAR rawbytes Message) VAR string A1; VAR string A2_1; VAR string A2_2; VAR string A2_3; VAR string A2_4; VAR string A2_5; VAR string A2_6; VAR string A2_7; VAR string A2_8; VAR string A2_9; VAR string A3; VAR string A4_1; VAR string A4_2; VAR string A4_3; VAR string A4_4; VAR string A4_5; VAR string A4_6; VAR string A5_End; VAR string ID; VAR state3d SysStatus; VAR byte Result; VAR num X; VAR num Y; VAR num Z; VAR num R; VAR num P; VAR num I; VAR bool ok; UnpackRawBytes Message,1,A1\ASCII:=30; UnpackRawBytes Message,31,A2_1\ASCII:=1; UnpackRawBytes Message,32,A2_2\ASCII:=1; UnpackRawBytes Message,33,A2_3\ASCII:=1; UnpackRawBytes Message,34,A2_4\ASCII:=1; UnpackRawBytes Message,40,A3\ASCII:=1; UnpackRawBytes Message,41,A4_1\ASCII:=7; UnpackRawBytes Message,49,A4_2\ASCII:=7; UnpackRawBytes Message,57,A4_3\ASCII:=7; UnpackRawBytes Message,65,A4_4\ASCII:=7; UnpackRawBytes Message,73,A4_5\ASCII:=7; UnpackRawBytes Message,81,A4_6\ASCII:=7; ProductID:=A1; SysStatus.valid:=StrToByte(A2_1); SysStatus.errno:=StrToByte(A2_2); SysStatus.jobstate:=StrToByte(A2_3); SysStatus.empty:=StrToByte(A2_4); Result:=StrToByte(A3); ok:=StrToVal(A4_1,A); ok:=StrToVal(A4_2,B); ok:=StrToVal(A4_3,C); ok:=StrToVal(A4_4,D); ok:=StrToVal(A4_5,E); ok:=StrToVal(A4_6,F); RETURN [ID,SysStatus,Result,[[A,B,C],[D,E,F]]]; ENDFUNC
-
Hallo,
bezüglich der Delimiter steht folgenden im Handbuch:
ZitatWenn das Argument \Delim verwendet wird, wird jedes Zeichen im angegebenen Zeichenfolge-Argument sowie standardmäßig auch Zeilenvorschubzeichen als signifikanter Teil der Zeile betrachtet.
Das heißt, bei Angabe von \Delim:="],[" erfolgt die Trennung beim Auftreten des Zeichens '[', ',' , ']' bzw. beim Zeilenvorschubzeichen (\0A), da jedes der Zeichen einzeln betrachtet wird und nicht der komplette String gesucht wird.
ZitatUm nicht alphanumerische Zeichen anzugeben, verwenden Sie \xx , wobei xx die hexadezimale Darstellung des ASCII-Codes für das Zeichen ist (Beispiel: TAB wird durch \09 angegeben).
Die Hex-Codes müssen laut Handbuch nur dann verwendet werden, wenn es sich um nicht darstellbare Zeichen handelt (Steuerzeichen: HEX 00 - HEX 1F). Alle anderen Zeichen können ganz normal angegeben werden (z.B ";")
-
Hi Micky
dacht mir schon das nicht so funktioniert wie bei string einfach ein + dazwischen.
Mit den Handbüchern ist das so immer eine Sache, oft überliest man die kleinen Wörter auf die es letztendlich aber ankommt.
Mein Ziel das umbenennen von Modulen hab ich jetzt aber aufgegeben, ist mir zu umständlich.
Da ich von den vielen Modulen eh immer nur eins laden muss, kann das Modul ja den gleichen Namen besitzen, da reicht es völlig aus wenn die Dateien im Home Verzeichniss einen unterschiedlichen Namen besitzen, das geht ja zum Glück Problemlos mit Save.
Dann einfach ins Modul noch einen String mit den Typnamen rein un gut is.
Werd jetzt diesen Weg verfolgen.
Hilfe und Support für ABB Roboter Programmierung, Konfiguration, Inbetriebnahme finden Sie hier im ABB Roboter Forum.
ABB Rapid Programmierung ist einfach, die Roboterforum Community hilft sehr gerne.
Erstelle ein Benutzerkonto oder melde dich an um zu kommentieren
Du musst ein Benutzerkonto haben um einen Kommentar hinterlassen zu können
Benutzerkonto erstellen
Neues Benutzerkonto für unsere Community erstellen. Geht einfach!
Neues Benutzerkonto erstellen