Worum geht es?
In AutoIt haben wir es oft mit tabellenartig strukturierten Daten zu tun.
Je nach Quelle müssen wir teils einen erheblichen Codeaufwand betreiben um die Daten in eine Form zu bringen, mit der wir weiterarbeiten können.
Anschließend wird das Arbeiten mit diesen Daten auch nicht unbedingt einfacher, da wir, anstatt auf die sprechenden Namen der Attribute der Daten zuzugreifen, wir es mit numerischen Indizes zu tun haben bei denen man sehr schnell die Übersicht verliert.
Beide Probleme werden durch die UDF adressiert.
Im Grundansatz arbeitet die UDF mit einem Table-Objekt (lediglich eine AutoIt-Map), in welcher die Daten vom Header getrennt werden.
Das ermöglicht eine sauberere Prozessierung der Daten.
Sie bietet Funktionen um aus verschiedenen Quellen Daten einzulesen (CSV, Array, string with fixed-width-columns, Strings mit eigenen Spaltentrennungen).
Innerhalb dieses Aufrufes werden die Daten vom Header getrennt oder diesen überhaupt erst Headerdaten hinzugefügt.
Die Daten werden dann entsprechend ihrem Format aufgearbeitet (bei csv Quotes und Escapes entfernt, bei fixed-width Leerräume entfernt...).
Darüber hinaus kann der User direkt für jede Spalte einzeln festlegen wie genau die Daten aufgearbeitet werden sollen. Er ist hierbei komplett frei.
Auf diese Art erhalten die Daten bereits beim Einlesen das Endformat in welchem sie weiterverarbeitet werden sollen.
Anschließend können die Daten spaltenbasiert oder Attributbasiert behandelt werden.
Sprich: Anstatt mit Indizes können auch einfach die Attributnamen der Daten verwendet werden - das ermöglicht eine bessere Übersichtlichkeit im Code.
Beispiel (umfangreiche weitere Beispiele im Unterordner "examples")
Wir möchten die offenen Ports auf einem Rechner mit AutoIt auswerten.
Der Kommandozeilenbefehl lautet hierfür netstat -t und bringt uns folgende Ausgabe (bei euch je nach System evtl. anders strukturiert):
Active Internet connections (w/o servers)
Proto Recv-Q Send-Q Local Address Foreign Address State
tcp 0 116 192.168.64.110:ssh 192.168.29.200:65069 ESTABLISHED
tcp 0 0 192.168.64.110:ssh 192.168.29.200:65068 ESTABLISHED
Um diese Daten sinnvoll weiterzuverarbeiten müssen wir gegebenenfalls folgende Schritte in AutoIt durchführen:
- Löschen der ersten unnützen Zeilen
- Extraktion der Kopfzeile (sie wird anders behandelt als die Daten)
- Erzeugung eines Arrays mit korrekter Dimension um die Daten zu halten
- Trennung der Daten entweder anhand von Leerräumen oder anhand der jeweils festen Spaltenbreite
- Befreiung der Daten von unnötigen Leerräumen
- Konvertierung der Recv-Q und Send-Q-Spalte in einen Zahlendatentyp (für Sortierung usw)
- Auftrennung der Adressdaten in IP-Adresse und Port
Das kann eine Menge (fehleranfälligen) Code-Aufwand bedeuten.
Mit dieser UDF hingegen kann man das ganze folgendermaßen in einem einzigen Aufruf lösen:
$sString = 'Active Internet connections (w/o servers)' & @CRLF & _
'' & @CRLF & _
'Proto Recv-Q Send-Q Local Address Foreign Address State' & @CRLF & _
'tcp 0 116 192.168.64.110:ssh 192.168.29.200:65069 ESTABLISHED' & @CRLF & _
'tcp 0 0 192.168.64.110:ssh 192.168.29.200:65068 ESTABLISHED'
; Transfer data to table type by using the size of every column:
Global $mData = _td_fromFixWidth($sString, _
"left 6; Number 7; Number 7; StringSplit($x, ':', 2) 24;StringSplit($x, ':', 2) 24;", _ ; column definitions
"1-2", _ ; skip row 1 to 2
True) ; first row = header
; display data
_td_display($mData)
Alles anzeigen
und wir erhalten als Resultat:
Wenn man nun Funktionen wie _td_toObjects() nutzt, dann kann man die einzelnen Daten mit Ausdrücken wie $aData.Proto oder $aData.State prozessieren.
Das sollte deutlich übersichtlicher sein als sich mit den Arrayindizes herumzuschlagen.
Funktionsumfang
Funktion | Beschreibung |
---|---|
Eingabe | |
_td_fromString | konvertiert einen Tabellenartig strukturierten String, bei welchem die Spaltentrenner über einen regulären Ausdruck beschrieben werden können, in ein Tabellenobjekt |
_td_fromCsv | Liest eine Datei oder String in ein Tabellenobjekt, welcher als csv, tsv oder ähnlichem (anpassbaren) Format strukturiert ist. |
_td_fromFixWidth | Konvertiert einen tabellenartig strukturierten String in ein Tabellenobjekt, bei dem die Spalten feste Zeichenbreiten haben (üblicherweise Konsolenausgaben oder printf-Tabellen) |
_td_fromArray | Erzeugt ein Tabellenobjekt aus einem vorhandenen Array |
Ausgabe | |
_td_toCsv | Konvertiert ein Tabellenobjekt in einen csv/tsv-formatierten String |
_td_toFixWidth | Konvertiert ein Tabellenobjekt in einen String, in welchem die Spalten feste Breiten haben |
_td_display | Stellt ein Tabellenobjekt ähnlich _ArrayDisplay dar (mit Headerbezeichnern und Sortiermöglichkeit) |
_td_toArray | Konvertiert ein Tabellenobjekt in ein 2D-Array bei welchem der Header in der ersten Zeile steht (wenn man nur die Daten haben möchte stattdessen $mTable.Data nutzen) |
Bearbeitung von Tabellen | |
_td_join | Verknüpft 2 Tabellenobjekte ähnlich wie ein SQL-Join |
_td_filter | Filtert Datensätze in Tabellenobjekten ähnlich zu einem SQL-Where |
Aufbereitung zur effizienteren Weiterbehandlung | |
_td_toObjects | Konvertiert ein Tabellenobjekt in eine Liste von Datenobjekten. Jeder Eintrag ist damit eine Map bei welcher die Attribute über den Namen angesprochen werden können. |
_td_MapsToTable | Konvertiert eine Liste von Maps (wie von _td_TableToMaps) in ein 2D-Array |
_td_toPrimaryKeys | Konvertiert ein Tabellenobjekt in eine Map für die Datensätze, bei welcher ein Primärschlüsselattribut der Daten als Key verwendet wird. (ermöglicht Zugriff auf die Daten mit Namen anstatt Indizes) |
_td_toColumns | Konvertiert ein Tabellobjekt in eine Map, welche als Einträge die einzelnen Spalten als 1D-Array enthalten. |
_td_getColumn | Extrahiert eine Spalte aus einem Tabellenobjekt |