Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

String.replaceAll() throwing IndexOutOfBoundsException

Tags:

java

I get java.lang.IndexOutOfBoundsException, when I call replaceAll() with replacement text containing $1:

This is from a more complex code, but I simplified it as follows:

http://ideone.com/QCof3

class Test {
    public static void main(String args[]) {
        String test = "@Key";
        String replacement = "$1";
        test = test.replaceAll("@Key", replacement);
        System.out.println(test);
    }
}


Exception in thread "main" java.lang.IndexOutOfBoundsException: No group 1
    at java.util.regex.Matcher.group(Matcher.java:470)
    at java.util.regex.Matcher.appendReplacement(Matcher.java:737)
    at java.util.regex.Matcher.replaceAll(Matcher.java:813)
    at java.lang.String.replaceAll(String.java:2189)
    at Test.main(Main.java:5)

Are there any workarounds for this issue? I do not want to use a 3rd party library.

like image 511
Caner Avatar asked Dec 13 '11 12:12

Caner


People also ask

What do the replaceAll () do?

The replaceAll() method returns a new string with all matches of a pattern replaced by a replacement .

What is the difference between Replace () and replaceAll ()?

The only difference between them is that it replaces the sub-string with the given string for all the occurrences present in the string. Syntax: The syntax of the replaceAll() method is as follows: public String replaceAll(String str, String replacement)


6 Answers

try with the replace() only

test = test.replace("@Key", replacement);
like image 70
Pratik Avatar answered Oct 21 '22 07:10

Pratik


String replacement = "\\$1";

should resolve it. $ is a regex control character, so just like any other control character it must be escaped. Java being java, the escape has to be a double backslash.

like image 39
mcfinnigan Avatar answered Oct 21 '22 06:10

mcfinnigan


If you really need the regex in String.replaceAll() instead of just the String.replace(), which really does replace all strings but just does not use regex, you can use Matcher.quoteReplacement()

String stringwithgroup = "Give me all your $$$$";
String result = proposal.replaceAll("Marry me",Matcher.quoteReplacement(stringwithgroup));
like image 32
Sean Moore Avatar answered Oct 21 '22 07:10

Sean Moore


    String test = "@Key";
    String replacement = "\\$1";
    test = test.replaceAll("@Key", replacement);
    System.out.println(test);

  • IDEOne Demo
like image 27
jmj Avatar answered Oct 21 '22 07:10

jmj


Check your regular expression. You want to catch the first group that was selected in your regular expression. But your regular expression is only $1. This means that it takes the first group. But there is no such group, so there is the exception.

 Exception in thread "main" java.lang.IndexOutOfBoundsException: No group 1

Try using this command with this regular expression.

Class Test {  
   public static void main(String args[]) {  
      String test = "@Key";  
      String replacement = "!!$1";  
      test = test.replaceAll("(@Key)", replacement);  
      System.out.println(test);  
   }  
}

The result is test = !!@Key. Because the first group is @Key and replacement by !!@Key.

Please check there links for rugular expressions. Lesson REGEX
And: Search and replace with regular expressions

Hope this help

like image 20
Anderson Carniel Avatar answered Oct 21 '22 07:10

Anderson Carniel


Solution

This is what you need to do:

String test = "@Key";
String replacement = "\\$1";
test = test.replaceAll("@Key", replacement);
System.out.println(test);

Use of $#

'$#', '#' being a number in the second argument of replaceAll means it will get the 1st group of matches. So to use it correctly, here's an example:

String test = "World Hello!!!";
String replacement = "$2 $1";
test = test.replaceAll("(World) (Hello)", replacement);
System.out.println(test);

You create groups with the brackets, and the code take the two groups and swap them around.

Use of $

'$' in regular expression means the end of the line. So by using '$' as the first argument in replaceAll, will append to the end of the string, ie:

String test = "World Hello!!!";     
test = test.replaceAll("$", " ~ a java dev");
System.out.println(test);
like image 32
JackDev Avatar answered Oct 21 '22 06:10

JackDev