問題は、あなたが一致しない可能性があり$(
と)
と一致していることです。 と一致するのは$(
で、$(
の後には)
が続きます。
解決方法1:一致しているときは、「外出先」$(...)
文字列にマッチし、マップからトークンを取得するために、それらの内側にテキストをキャプチャし、置換を実行するために、単純な正規表現を使用することができますMatcher#appendReplacementCallback
の使用:
SortedMap<String, String> map = new TreeMap<String, String>();
map.put("test", "REPLACE");
String update = "$(test) (test) (test2)";
Matcher m = Pattern.compile("\\$\\(([^)]*)\\)").matcher(update);
StringBuffer sb = new StringBuffer();
while (m.find()) {
m.appendReplacement(sb, map.getOrDefault(m.group(1), m.group(1)));
}
m.appendTail(sb);
System.out.println(sb);
IDEONE demo
解決策2を参照してください:Split
と前後参照
でラムダを使用します
免責事項:この方法は、あまりにも長い文字列にのみ有効です。
また、ルックアラウンドを使用することもできます。先読みで、問題はない、それは無限の幅です。後読みでは、我々は(代わりに+
または*
の限定数量詞を使用して)制約幅後読みに頼ることができます。今すぐ読み
SortedMap<String, String> map = new TreeMap<String, String>();
map.put("test", "REPLACE");
String update = Arrays.stream("$(test) (test) (test2)"
.split("\\$\\((?=[^)]*\\))|(?<=\\$\\([^(]{0,1000})\\)"))
.map(token -> map.getOrDefault(token, token))
.collect(Collectors.joining(""));
System.out.println(update); // => REPLACE (test) (test2)
がIDEONE demo
正規表現を参照してください:
\$\((?=[^)]*\))
- $(
に続いて、)
以外の0文字が続き、次に)
以外の文字が続きます10
|
- 又は
(?<=\$\([^(]{0,1000})\)
から$(
で先行さ(
以外0-1000(それが十分でなければならない)文字で先行する)
と一致。
'split'がセパレータを削除します。 – Savior
を試してみてください。http://stackoverflow.com/a/2206432/1214800 – brandonscript
あなたは最初に '$('しかし、あなたのコードは実際には '($ $。 – Jesper