1

I am quite new to java. I am wondering if it is possible to check for a certain number of consecutively repeated characters (the 'certain number' being determined by the user) in a string or an index in a string array. So far I have tried

int multiple_characters = 0;
String array1 [] = {"abc","aabc","xyyyxy"};
for (int index = 0; index < array1.length;i++){
   for (int i = 0;i<array1[index].length;i++){
      if (array1[index].charAt(i) == array1[index].charAt(i+1)){
         multiple_characters++;
      }
   }
}

But with this I get a StringIndexOutOfBounds error. I tried fixing this by putting in an extra if statement to make sure i was not equal to the array1[index].length, but this still threw up the same error. Other than the manual and cop-out method of:

if ((array1[index].charAt(i) == array1[index].charAt(i+1) && (array1[index].charAt(i) == array1[index].charAt(i+2))

and repeating however many times, (which would not be great for quick changes to my code), I can't seem to find a solution.

Malted_Wheaties
  • 132
  • 1
  • 10

3 Answers3

2

For the inner for loop (the one with the i variable), you're then calling string.charAt(i+1) where ii loops from 0 to the length of that string.

No wonder you get an index array out of bounds exception, you're asking for the character AFTER the last.

I advise that you try to understand the exception, and if you can't, debug your code (step through it, one line at a time, and if you don't know how to use a debugger, add println statements, checking what the code does what with you think it does. There where your code acts differently from your expectation? That's where the bug is).

This plan of 'oh, it does not work, I'll just chuck it out entirely and find another way to do it' is suboptimal :) – go back to the first snippet, and just fix this.

rzwitserloot
  • 85,357
  • 5
  • 51
  • 72
1

You are getting StringIndexOutOfBoundsException because you are trying to access string.charAt(i + 1) where i goes up to the highest index (i.e. string.length() - 1) of string.

You can do it as follows:

class Main {
    public static void main(String[] args) {
        int multiple_characters = 0;
        int i;
        String array1[] = { "abc", "aabc", "xyyyxy" };
        for (int index = 0; index < array1.length; index++) {
            System.out.println("String: " + array1[index]);
            for (i = 0; i < array1[index].length() - 1; i++) {
                multiple_characters = 1;
                while (array1[index].charAt(i) == array1[index].charAt(i + 1) && i < array1[index].length() - 1) {
                    multiple_characters++;
                    i++;
                }
                System.out.println(array1[index].charAt(i) + " has been repeated consecutively " + multiple_characters
                        + " time(s)");
            }
            if (multiple_characters == 1) {
                System.out.println(array1[index].charAt(i) + " has been repeated consecutively 1 time(s)");
            }
            System.out.println("------------");
        }
    }
}

Output:

String: abc
a has been repeated consecutively 1 time(s)
b has been repeated consecutively 1 time(s)
c has been repeated consecutively 1 time(s)
------------
String: aabc
a has been repeated consecutively 2 time(s)
b has been repeated consecutively 1 time(s)
c has been repeated consecutively 1 time(s)
------------
String: xyyyxy
x has been repeated consecutively 1 time(s)
y has been repeated consecutively 3 time(s)
x has been repeated consecutively 1 time(s)
y has been repeated consecutively 1 time(s)
------------
Arvind Kumar Avinash
  • 71,965
  • 6
  • 74
  • 110
1

If I was to look for repeated characters, I would go the regular expression route. For example to look for repeated a characters (repeated twice in this example), you could have:

import java.util.regex.Pattern;

public class Temp {
  public static void main(final String[] args) {
    String array1 [] = {"abc","aabc","xyyyxy"};
    for (String item : array1){
      if (Pattern.compile("[a]{2}").matcher(item).find()) {
        System.out.println(item + " matches");
      }
    }
  }
}

In this extract, the reg exp is "[a]{2}" which looks for any sequence of a characters repeated twice. Of course more complicated regular expressions are required for more complex matches, good resources to explain this may be found here: https://docs.oracle.com/en/java/javase/11/docs/api/java.base/java/util/regex/Pattern.html
Another point is that for efficiencies sake, it is often practise to move the: Pattern.compile(*Pattern*) outside of the method call, e.g. to a final static field

This stack overflow:
RegEx No more than 2 identical consecutive characters and a-Z and 0-9
gives quite a detailed description of the regular expression issues involved with this problem.

Bill Naylor
  • 482
  • 1
  • 9
  • 14
  • Can it be used to count the number of repetitions? – Scratte Jan 26 '20 at 02:10
  • Well regular expressions are quite complex beasts and I would try experimenting. The API docs are a good starting point, so the first URL I gave along with the Matcher API: https://docs.oracle.com/javase/7/docs/api/java/util/regex/Matcher.html I notice there are methods in the later, start() and end(), which might help you? – Bill Naylor Jan 26 '20 at 09:58
  • 1. There are more recent version of java than java7. I'd probably go to at least a javadoc for java9 that comes with a search field. 2. While regex has it's advantages, I find them somewhat hard to read with the brain-braking-factor increasing with the length of the regex. While it's a great learning experience to fiddle with one for hours on end, it can get to a discouraging point. `X{n,}` would seem to be a way to go, but I doubt you can make the regex give you the actual number of repetitions, which leaves you with having to make a manual count of the resulting string. – Scratte Jan 26 '20 at 11:11
  • Sure there are more recent versions of java, but as far as I know the `Matcher` and `Pattern` classes have not changed to any large extent. https://docs.oracle.com/en/java/javase/11/docs/api/java.base/java/util/regex/Matcher.html I just noticed a method `toMatchResult`, which returns an `MatchResult`, which has the method: groupCount() Returns the number of capturing groups in this match result's pattern. So I would imagine you could use that. – Bill Naylor Jan 26 '20 at 12:00