-1

I created a method which takes an Arraylist of string and an integer. It's going to remove all string whose length is less than the given integer.

For example:

Arraylist = ["abcde", "aabb", "aaabbb", "abc", "ab"]

integer = 4

So the new Arraylist should be: ["abcde", "aabb", "aaabbb"]

But I'm getting this error message:

Exception in thread "main" java.lang.IndexOutOfBoundsException: Index 3 out of bounds for length 3

Here is my code:

public static void main(String[] args){
        ArrayList<String> newArrayList = new ArrayList<>();
        newArrayList.add("string1");
        newArrayList.add("string2");
        newArrayList.add("rem");
        newArrayList.add("dontremove");
        removeElement(newArrayList, 4); // new arraylist must be = [string1, string2, dontremove]
    }


    public static void removeElement(ArrayList<String> arraylist, int inputLen){
        int arrayLen = arraylist.size();
        for(int i=0; i<arrayLen; i++){
            if(arraylist.get(i).length() < inputLen){
                arraylist.remove(i);
                i--;
            }
        }
        System.out.println("New Arraylist: " + arraylist);
    }

What's wrong with this code?

Mureinik
  • 297,002
  • 52
  • 306
  • 350
erenoz
  • 15
  • 1
  • 3
  • Aside from your logic error, the name `removeElement` indicates that your method will remove the 4th element. Instead, a name like `removeElementsLongerThan` would be more helpful to people reading your code. Additionally, you should normally not declare variables and parameters as `ArrayList`; [just use `List`](https://stackoverflow.com/questions/383947/what-does-it-mean-to-program-to-an-interface). – chrylis -cautiouslyoptimistic- Jan 02 '21 at 21:45

4 Answers4

4

You're looping from 0 to the size of the array which is 4. Inside the loop you're removing items so the size of the array becomes less than 4, so you get this exception. Try looping like this:

Iterator<String> iterator = arraylist.iterator();

while (iterator.hasNext()) {
    String word = iterator.next();
    if (word.length() < inputLen) {
        iterator.remove();
    }
}
chrylis -cautiouslyoptimistic-
  • 75,269
  • 21
  • 115
  • 152
Rony Tesler
  • 1,207
  • 15
  • 25
  • 1
    Yeah i know it's like a different way to solve this problem. But I wanted to solve this problem using the way that i used. Like using "for" statement. Thank you very much for your helps. – erenoz Jan 02 '21 at 22:20
  • @erenoz If you want to use a "for" loop, don't change the list you're looping while looping it. Inside the loop, you can add to a new list the items you want to remove, then remove them after the "for" loop. – Rony Tesler Dec 30 '21 at 02:30
2

You're modifying the list while iterating over its indexes. Once you remove the first item, the list will be shorter than you expect, and you'll get this error once you reach the index of the original last element. Luckily, the removeIf method can do the heavy lifting for you:

public static void removeElement(List<String> arraylist, int inputLen) {
    arraylist.removeIf(s -> s.length() < inputLen);
    System.out.println("New Arraylist: " + arraylist);
}
Mureinik
  • 297,002
  • 52
  • 306
  • 350
1

The length of the array should change when you remove elements. The arrayLen variable stores the length of the array, but doesn't change when the array's length shrinks. To change it, you should be able to just replace arrayLen with arrayList.size(), which will change when your remove elements

Ryan Yanko
  • 46
  • 1
  • 1
0
int arrayLen = arraylist.size();

The problem is that your index has a value of 4.

But then as soon as you remove an item from the list you now only have 3 entries.

So in your loop when you try to access the the 4th entry you will now get an IndexOutOfBounds error.

The solution is to start at the end of the ArrayList and count down to 0.

For (int i = arrayLen - 1; i >= 0; i--)

and inside the loop you don't need the:

i--;
camickr
  • 321,443
  • 19
  • 166
  • 288
  • No, the solution is to use an iterator. Your proposal is still likely to throw `ConcurrentModificationException`. – chrylis -cautiouslyoptimistic- Jan 02 '21 at 21:42
  • @chrylis-cautiouslyoptimistic-, no it won't throw a ConcurrentModificationException. It is not using a foreach. All the code does is access an item in the ArrayList. The ArrayList doesn't know or care that the code is executing in a loop. – camickr Jan 02 '21 at 21:54