2017-11-17 2 views
0

Ich habe die folgende Methode, die alle Vorkommen einer {TIMESTAMP} Teilzeichenfolge mit dem Wert von String.valueOf(System.nanoTime()) zurückgegeben wird, die Absicht ist, eine andere Zeitmarke pro Teilzeichenfolge zu erhalten, aber es resultiert in allen Teilstrings wird nur durch den gleichen Wert ersetzt.Ersetzen Sie alle Vorkommen einer Teilzeichenfolge einzeln nacheinander

class StringUtils { 
    private static String resolveTimestamp(String s) { 
     String timestamp = "\\{TIMESTAMP}"; 
     return s.replaceAll(timestamp, String.valueOf(System.currentTimeMillis())); 
    } 
} 

class Sample { 
    public static void main(String[] args) { 
     StringUtils.resolveTimestamp("{TIMESTAMP}, {TIMESTAMP}, {TIMESTAMP}") 
    } 
} 

// The execution of the code above would result in: 
// 241170886964203, 241170886964203, 241170886964203 

// But I want to get this: 
// 241733154573329, 241734822930540, 241751957270934 

Ich möchte wissen, welche ist die beste Art und Weise zu tun, was ich will, wie es mehrere Möglichkeiten zu tun, dass gerade jetzt meiner Meinung nach kommen:

  • Eine Schleife mit s.matches(timestamp) als Bedingung Iterieren über jedes Vorkommen der Teilzeichenfolge und s.replaceFirst(timestamp, String.valueOf(System.nanoTime())), um das Ersetzen innerhalb der Schleife durchzuführen.
  • den Teil Verwenden Sie die Zeichenfolge in mehrere Stücke mit s.split(timestamp) und iterieren die Stücke verbinden jedes Paar mit dem Wert von String.valueOf(System.nanoTime()))
  • wahrscheinlich einigen anderen Möglichkeiten

Hinweis zurück zu explodieren: Bitte beachten Sie, dass diese ist nicht das gleiche Problem adressiert in this question. Dort müssen sie mehrere Vorkommen eines festen Musters durch den gleichen Wert ersetzen, während ich mehrere Vorkommen desselben Teilzeichens durch jeweils einen anderen zur Laufzeit berechneten Wert ersetzen muss.

+3

Welchen anderen Wert wünschen Sie? 'currentTimeMillis()' gibt wahrscheinlich den gleichen Wert zurück, wenn Sie ihn über einen kurzen Zeitraum aufrufen. – markspace

+1

Sofern Sie nicht eine große Anzahl von Zeitstempeln (Zehntausende) in einer einzigen Zeichenfolge ersetzen, macht es keinen Unterschied, ob Sie sie einzeln oder alle gleichzeitig ausführen. Es wird alles innerhalb von weniger als einer Millisekunde passieren, so dass Sie trotzdem den gleichen Wert erhalten. Manchmal erhalten Sie Werte, die sich an der letzten Stelle um 1 unterscheiden, wenn Sie eine Millisekundengrenze überschreiten. Ich denke, das ist ein [XY-Problem] (http://xyproblem.info) –

+0

Mögliches Duplikat von [java regulären Ausdruck suchen und ersetzen] (https://stackoverflow.com/questions/9605716/java-regular-expression-find -und-replace) –

Antwort

2

können Sie String.replaceFirst verwenden:

private static String resolveTimestamp(String s) { 
    String timestamp = "\\{TIMESTAMP}"; 

    while(s.matches(timestamp)) { 
     s = s.replaceFirst(timestamp, String.valueOf(System.nanoTime())); 
    } 
    return s; 
} 
+1

Es ist wahrscheinlich effizienter, ['Matcher.appendReplacement'] zu verwenden (https://docs.oracle.com/javase/8/docs/api/java/util/regex/Matcher.html#appendReplacement-java.lang. StringBuffer-java.lang.String-) gefolgt von einem 'appendTail'. –

+0

@MarkRotteveel Ich wusste nicht, wie diese Klasse funktioniert. – baudsp

+0

@baudsp Ich habe die Frage bearbeitet, 'System.nanoTime()' anstelle von 'currentTimeMillis()' zu verwenden, da Letzteres wahrscheinlich den gleichen Wert für mehrere Aufrufe zurückgibt. Können Sie Ihre Antwort bearbeiten, um sie als Lösung zu markieren? Danke – beni0888

2

Klingt wie das, was Sie tun möchten, ändern wird: replaceAll mit replaceFirst auf diese Weise jedes Mal, wenn die Methode mit dem String nennen wollen - es ist nur das nächste Vorkommen ersetzen:

public static void main(String[] args) { 
    String req = "\\{TIMESTAMP} \\{TIMESTAMP} \\{TIMESTAMP} \\{TIMESTAMP}"; 
    req = resolveTimestamp(req); 
    req = resolveTimestamp(req); 
    req = resolveTimestamp(req); 
    req = resolveTimestamp(req); 
    System.out.println("req = " + req); 
} 

private static String resolveTimestamp(String s) { 
    String timestamp = "\\{TIMESTAMP}"; 
    return s.replaceFirst(timestamp, String.valueOf(System.currentTimeMillis())); 
} 

OUTPUT:

req = \1510940324918 \1510940324921 \1510940324921 \1510940324921 

Kommentar: Sie sollten mit System.nanoTime() statt 0.123.958 betrachtenwenn Sie eine bessere Präzision wünschen.

+0

'System.nanoTime()' gibt keinen Zeitstempel im herkömmlichen Sinne zurück. Es beginnt mit einem willkürlichen Offset. – shmosel

+0

@smosel du hast recht, ich habe "bessere Genauigkeit" auf "bessere Präzision" korrigiert. – alfasin

0

Sie benötigen eine Methode aufrufen eine zufällige Zeichenfolge in Ihrem ersetzen alle Verfahren zurückzukehren.

str.replaceAll("timestamp", randomTimestamp()); 

private String randomTimestamp() { 
    Random rand = new Random(); 
    int randomNumber= rand.nextInt(1000); 
    return String.valueOf(System.currentTimeMillis() + randomNumber); 
} 
Verwandte Themen