Domino 9 und frühere Versionen > ND9: Entwicklung
Kleine Fingerübung - Daten in Textfile parsen
eknori (retired):
Ich sitze gerade an einem Stück Code, und mich ärgert insbesondere die Kurzsichtigkeit der Ersteller der Daten ( namentlich IBM )
Die Datei einthält in der ersten Zeile die "Spaltenköpfe", und in den Zeilen 2 -n die Daten dazu.
Alles kein Problem, schon 100x gemacht. Nur leider wird IMHO ein ungeeigneter Delimiter verwendet. Einen Doppelpunkt zu verwenden, wenn die Daten auch Date/Time Werte enthalten können, das ist nicht sonderlich klug. Und es macht das Parsen solcher Daten nicht gerade einfacher.
Ich habe hier ein beispiel, wie die Header und Daten aussehen können ( Das Beispiel ist schon eine bereinigte Version der Rohdaten )
Was ich erreichen möchte ist eine Map aus den daten zu generieren, die als KEY den Header enthält und als WERT den korrespondierenden Eintrag im Datenstring.
--- Code: ---package de.eknori.sandbox;
public class FileParser {
private static String HEADERS = "User:Device:SMS Address:Nonce:Time Created:Time Requested:Time Executed:Security Flags:Security Flags Failed:Failure Reason Code:Requester ID:Approval State:Approver ID:Approval Time";
private static String DATA1 = "CN=Kevin Kannix/OU=dau/O=dummstadt:FT88TDH7KP7V91GCH6R97MSLKO:null:2815699590:Tue Mar 07 09:13:02 CET 2017:Never:Never:none:none:0:null:Not required:null:Never";
private static String DATA0 = "CN=Kevin Kannix/OU=dau/O=dummstadt:FT88TDH7KP7V91GCH6R97MSLKO:null:2815699590:Never:Never:Never:none:none:0:null:Not required:null:Never";
public static void main(String[] args) {
try {
String[] headers = {};
headers = HEADERS.split(":");
String[] values = {};
values = DATA0.split(":");
int i = 0;
for (String header : headers) {
System.out.println(header.toUpperCase() + " = " + values[i]);
i++;
}
} catch (Exception e) {
e.printStackTrace();
}
}
}
--- Ende Code ---
Sieht dann für DATA0 so aus ( ist keine Map, weiss ich )
--- Code: ---USER = CN=Kevin Kannix/OU=dau/O=dummstadt
DEVICE = FT88TDH7KP7V91GCH6R97MSLKO
SMS ADDRESS = null
NONCE = 2815699590
TIME CREATED = Never
TIME REQUESTED = Never
TIME EXECUTED = Never
SECURITY FLAGS = none
SECURITY FLAGS FAILED = none
FAILURE REASON CODE = 0
REQUESTER ID = null
APPROVAL STATE = Not required
APPROVER ID = null
APPROVAL TIME = Never
--- Ende Code ---
Nimmt man DATA1 dann ist das Ergebnis natürlich völlig unsinnig.
--- Code: ---USER = CN=Kevin Kannix/OU=dau/O=dummstadt
DEVICE = FT88TDH7KP7V91GCH6R97MSLKO
SMS ADDRESS = null
NONCE = 2815699590
TIME CREATED = Tue Mar 07 09
TIME REQUESTED = 13
TIME EXECUTED = 02 CET 2017
SECURITY FLAGS = Never
SECURITY FLAGS FAILED = Never
FAILURE REASON CODE = none
REQUESTER ID = none
APPROVAL STATE = 0
APPROVER ID = null
APPROVAL TIME = Not required
--- Ende Code ---
Was wäre euer Ansatz?
Bei den möglichen Date/Time Feldern steht immerhin ein TIME im header :)
Tode:
Ich glaube, ich würde ,mit einem Regex- Replace alle Vorkommnisse von " \d\d:\d\d:\d\d " durch z.b. " \d\d~\d\d~\d\d~ " ersetzen lassen.
Nach dem Parsen dann wieder umbenennen. Dann bist Du nicht auf den "korrekten" Header angewiesen.
Ansonsten müsstest Du wirklich von links nach rechts gehen und immer "alles rechts vom nächsten Doppelpunkt" nehmen, und den Wert dann prüfen, ob er "Never" oder eben ein Datumswert ist... ziemlich aufwändig...
eknori (retired):
soo aufwändig ist es jetzt auch wieder nicht
--- Code: --- public static void main(String[] args) {
try {
String[] headers = {};
headers = HEADERS.split(":");
String[] values = {};
values = DATA1.split(":");
int i = 0;
for (String header : headers) {
if (header.toUpperCase().contains("TIME") && !values[i].equalsIgnoreCase("never")) {
System.out.println(
header.toUpperCase() + " = " + values[i] + ":" + values[i + 1] + ":" + values[i + 2]);
i = i + 2;
} else {
System.out.println(header.toUpperCase() + " = " + values[i]);
}
i++;
}
} catch (Exception e) {
e.printStackTrace();
}
}
--- Ende Code ---
eknori (retired):
Bleibt noch zu klären, was auf einem französichen Server mit bulgarischem Datumsformat im OS und installiertem türkischen LP, betrieben durch eine US Firma mit deutschem Admin passiert
eknori (retired):
@Thorsten:
Aber deine Lösung ist natürlich eleganter; spart einiges an zusätzlichem Kram
--- Code: --- String[] headers = {};
headers = HEADERS.split(":");
String[] values = {};
values = DATA0.replaceAll("(\\d{1,2}):(\\d{1,2}):(\\d{1,2})", "$1#$2#$3").split(":");
int i = 0;
for (String header : headers) {
System.out.println(header.toUpperCase() + " = " + values[i].replaceAll("#", ":"));
i++;
}
--- Ende Code ---
Navigation
[0] Themen-Index
[#] Nächste Seite
Zur normalen Ansicht wechseln