16

私はこのコードを書きました:

public static void main(String args[]) throws Exception {
    String template = "The user has spent amount in a day";
    String pattern = "amount";
    String output = template.replaceAll(pattern, "$ 100");
    System.out.println(output);
}

これを実行すると、次のようになります。

Exception in thread "main" java.lang.IllegalArgumentException: Illegal group reference
        at java.util.regex.Matcher.appendReplacement(Matcher.java:713)
        at java.util.regex.Matcher.replaceAll(Matcher.java:813)
        at java.lang.String.replaceAll(String.java:2190)
        at demo.BugDemo.main(BugDemo.java:16)
Java Result: 1

ファイルからデータを読み取っています。$ファイル データ内のすべてのシンボルをエスケープする必要がありますか、それとも不要なプロセスですか? この状況を処理する他のクラスまたはライブラリはありますか?

(正規表現ではなく) 置換テキストに特別な記号があることの問題は何ですか?

ノート:

  • エスケープするためにすべての文字をチェックしたくありません。それが私がこの質問をしている理由です。

  • 私はJava 6を使用しています。

4

5 に答える 5

32

String.replaceAll正規表現マッチングパターンを最初のパラメーターとして取り、正規表現置換パターンを 2 番目のパラメーターとして取り、正規表現$で特定の意味を持ちます (意味は異なりますが、マッチング パターンと置換パターンの両方で)。

代わりに使用するだけString.replaceで、すべての問題が解消されると思います。replaceAll正規表現を介して本当に一致/置換したい場合にのみ使用する必要があります-この場合はそうしないと思います。

編集:あなたの質問に関して:

(正規表現ではなく) 置換テキストに特別な記号があることの問題は何ですか?

繰り返しますが、のドキュメントreplaceAllはこれを明確にしています:

置換文字列にバックスラッシュ (\) とドル記号 ($) を使用すると、リテラル置換文字列として扱われる場合とは結果が異なる場合があることに注意してください。を参照してくださいMatcher.replaceAllMatcher.quoteReplacement(java.lang.String)必要に応じて、これらの文字の特別な意味を抑制するために使用します。

したがって、一致するパターンを正規表現として扱いたいが、置換として扱いたくない場合は、 を使用しますMatcher.quoteReplacement

于 2013-01-04T07:18:46.677 に答える
7

置換文字列で$は、特殊文字です。置換するパターンから一致したグループを取得するために使用されます。詳細については、こちらをご覧ください。

これを修正するには、置換文字列を引用符で囲み、文字からすべての特別な意味を削除します$

import java.util.regex.Matcher;
// ...
String output = template.replaceAll(pattern, Matcher.quoteReplacement("$ 100"));
于 2013-01-04T07:18:28.437 に答える
1

これを試してみてください

 String template = "The user has spent amount in a day";
 String pattern = "amount";
 String output = template.replaceAll(pattern, "\\$ 100");
 System.out.println(output);
于 2013-01-04T07:23:06.750 に答える
0

$置換グループを指定する記号を使用します。あなたはそれをエスケープする必要があります:

String output = template.replaceAll(pattern, "\\$ 100");
于 2013-01-04T07:20:47.510 に答える