首页 > 解决方案 > 字符串索引超出范围:22 异常 Java

问题描述

我不断让字符串索引越界:22 异常。谁能告诉我我做错了什么?这是代码:

class Troll {
    private static final char[] VOWELS = {'a', 'A', 'e', 'E', 'i', 'I', 'o', 'O', 'u', 'U'};

    public static String disemvowel(String str) {
        int lengthStr = str.length();
        int lengthVOWELS = VOWELS.length;

        for (int i = 0; i < lengthStr; ++i)
            for (char vowel : VOWELS)
                if (str.charAt(i) == vowel)
                    str = removeChar(str, i);

        return str;
    }

    private static String removeChar(String str, int index) {
        return str.substring(0, index) + str.substring(index + 1);
    }
}

我在这里要做的是编写一个函数,该函数接受一个字符串并返回一个删除所有元音的新字符串。

标签: javastringexceptionindexoutofboundsexception

解决方案


当你把一个字符串变短时,你会减少它的长度。但是您正在存储初始字符串长度,并将其用作循环绑定。

更改i < lengthStri < str.length()


这解决了部分问题,即IndexOfOfBoundsException. 另一个问题是,删除一个字符后,您还需要确保完全检查下一个字符。

考虑字符串aa

  • 您会找到a位置 0,然后将其删除。
  • 下一个a现在在位置 0;你会跳过检查它是否是元音
  • 接下来,您将移动到检查位置 1。

如果您按照检查顺序(例如aeiou)对包含的元音进行字符串处理,它会起作用,但通常不是。

删除一个字符后,您需要停止循环遍历其他元音,然后递减i,以确保您检查删除的字符之后的字符:

    for (int i = 0; i < lengthStr; ++i) {
        for (char vowel : VOWELS) {
            if (str.charAt(i) == vowel) {
                str = removeChar(str, i);
                // Decrement i, so it gets incremented back to the
                // same value on the next iteration of the outer loop.
                --i;
                break;  // Break out of vowels loop.
            }
        }
    }

但是,这是解决问题的一种非常低效的方法:每次删除一个元音时,都会重建字符串的其余部分,包括随后要删除的所有元音。

如果您想在没有正则表达式的情况下执行此操作,最好的方法是创建一个StringBuilder,并且只添加非元音:

StringBuilder sb = new StringBuilder(lengthStr);
for (int i = 0; i < lengthStr; ++i) {
  char c = str.charAt(i);
  if (!isVowel(c) {
    sb.append(c);
  }
}
str = sb.toString();

whereisVowel是返回给定char是否为元音的方法,例如

boolean isVowel(char c) {
  return "aAeEiIoOuU".indexOf(c) >= 0;
}

推荐阅读