0

I should first of all say this is an assignment that is confusing me, I've already corrected one of the questions by the lecturer :/

Anyway, I've made a method which counts the words using booleans, a while loop and a counter.

However I need to some how shape this into a recursive method that counts the amount of words in a string, a word is delimited by one or many spaces.

countWords(" hello this is an example", 0); // returns 5

As you can see the only parameters are countWords(String s, int i) making it more difficult.

Also, within the method I'm restricted to only using these three methods s.charAt(0), s.substring(1) and s.equals("") again making it more of a head hurter :)

This is the none recursive method I wrote using a while loop:

public static int countWords(String s) {
    int words = 0;
    boolean spaceBefore = true;
    boolean spaceCurrently = false;
    while(true) {
        if (s.equals(""))
            return words;

        if (s.charAt(0) == ' ')
            spaceCurrently = true;
        else
            spaceCurrently = false;

        if (spaceBefore && !spaceCurrently)
            words++;        

        spaceBefore = spaceCurrently;
        s = s.substring(1);
    }
}
4

3 回答 3

2

好吧,因为这是一个家庭作业,我不会给你代码。但我会向你解释解决方案。看看你是否可以从中重建代码。

在该方法中,首先删除行首和行尾的空格,因为我们想忽略它。使用该trim()方法。接下来检查字符串是否为空字符串 ( ""),就像您在代码中所做的那样。如果是,则返回零,因为空字符串不包含单词,否则在无限循环 ( while (true)) 中检查以下条件:

  • 创建一个变量来保存当前索引,该索引不是循环本地的,而是方法本地的。对于无限循环的每次迭代,检查当前字符(使用charAt()方法)是否不是空格以及索引是否小于字符串的长度。如果此条件为真,则递增索引变量。
  • 如果不是,请检查索引变量是否等于字符串的长度。如果是,则返回 1,因为这意味着我们已经到达字符串的最后一个单词。
  • 如果不是,则返回 1 的总和和计算单词的方法,从 index 的当前值递归调用子字符串。

这应该为您带来价值。如果您仍然无法做到这一点,请告诉我,我会给您来源。

编辑好吧,如果您不能使用 String 的 trim 方法,您可以像这样为自己编写一个。我相信它不会违反您的任何要求:

private String trim(String str) {
    int beginIndex = 0;
    int endIndex = str.length() - 1;

    while (true) {
        if (str.charAt(beginIndex) == ' ') {
            beginIndex++;
        } else if (str.charAt(endIndex) == ' ') {
            endIndex--;
        } else {
            break;
        }
    }

    return str.substring(beginIndex, endIndex);
}

编辑 2如果你不能使用length()任何一个,那么修改上面的代码行int endIndex = str.length() - 1;' toint endIndex = getLength(str) - 1;` 并使用下面的代码来计算长度。

private int getLength(String str) {
    int length = 0;

    while (true) {
        try {
            str.charAt(length++);
        } catch (StringIndexOutOfBoundsException e) {
            break;
        }
    }
    return --length;
}

编辑 3由于问题是这样一个 PITA,因此很难用语言解释。所以这里是代码:

private int countWords(String searchString) {
    int index = 0;
    boolean beginning = true;       // to check if it's the beginning of the line

    if (searchString.equals("")) {
        return 0;
    } else {
        while (true) {
            try {
                if (searchString.charAt(index) != ' ') {
                    beginning = false;
                    index++;
                } else {
                    if (!beginning) {
                        return 1 + countWords(searchString.substring(++index));
                    } else {
                        return countWords(searchString.substring(++index));
                    }
                }
            } catch (StringIndexOutOfBoundsException e) {
                if (!beginning) {
                    return 1;
                } else {
                    return 0;
                }
            }
        }
    }
}

这将帮助您仅使用您被允许使用的方法来实现您想要的。

于 2013-02-11T12:42:47.470 回答
0

我不会直接发布代码,因为这是您的任务,但这里有一些指导。

字符串中的单词数是当前单词+字符串其余部分中的单词数。由于您当时只能处理一个字符,因此您可以这样想:

  • 有一个参数告诉你是否在一个词中
  • 如果 s.charAt(0) 是一个空格并且您在一个单词中,那么您将增加计数器并将 inWord 设置为 false
  • 如果 s.charAt(0) 是一个字母并且您不在一个单词中,那么您将 inWord 设置为 true
  • 使用更新的计数器和 s.subString(1) 进行递归并更新 inWord

然后你用 0, s, false 开始一切

想象一下将循环转换为递归,将变量从循环外部移动到方法参数中。

我希望这不会太混乱。

于 2013-02-11T12:20:30.990 回答
0

鉴于这是作业,我不会直接给你答案。

如果方法调用自身的机制,则递归。显然,如果一个方法不确定地执行此操作,您最终会得到一个 stackoverflow 异常,因此您需要某种退出条件,该方法停止调用自身。

这是一个示例 - 假设您想编写一个乘法方法,它接受两个数字并将它们相乘,但您只能使用加法和减法。

public int multiply(int value1, int value2) 
{
  if (value1 > 1) 
  {
    int remaining = value1 - 1;
    return value2 + multiply(remaining, value2);
  }
  else 
  {
    return value2;
  }
}

在这里,该方法调用自身,直到它添加value2到自身value1时间,此时它返回堆栈。

您可以做一些与您的字数统计类似的事情 - 继续调用该方法,传递从第一个空格到字符串末尾的子字符串,直到字符串中没有更多空格,此时返回堆栈。

于 2013-02-11T12:20:42.987 回答