【问题标题】:Recursion in helper methods (Java)辅助方法中的递归(Java)
【发布时间】:2014-11-06 00:52:26
【问题描述】:

我正在练习递归并使用递归辅助方法。在我的辅助方法中,出现一个错误,提示

Tree 类型中的 someMethod(K) 方法不适用于参数 (K, List, int)。

但是,我不想使用someMethod(K k) 方法,因为我正在尝试使用someMethod(K k, List<K> L, int n) 辅助方法。如何让 Eclipse “知道”我正在尝试使用其他方法?

这是我目前所拥有的:

public List<K> someMethod(K k) {
    List<K> L=new LinkedList<K>();
    if (lookup(k) != null) {
        return someMethod(k, L, 0);
    }
    return L;
}

private List<K> someMethod(K k, List<K> L, int n) {
    if (this.k.compareTo(k) == 0) {
        L.add(this.k);
        return list;
    }
    if (this.k.compareTo(k) < 0) {
        right.someMethod(k, L, n); //error here
        L.add(this.k);
    }
    if (this.k.compareTo(k) > 0) {
        left.someMethod(k, L, n); //error here
        L.add(this.k);
    }
}

编辑: 左右声明:

private Tree<K, V> left, right;

【问题讨论】:

  • 这只是来自 Eclipse 的一个注释还是程序实际上没有编译?
  • 好吧,当我尝试运行该项目时,它说有错误,所以我猜该程序实际上并没有因此而编译。我没有其他错误。
  • 请向我们展示leftright的声明。
  • 此外,递归辅助方法使用完全相同的参数调用自己,有令人讨厌的堆栈溢出倾向。
  • 什么是Tree?那是包含someMethod 的类吗?我认为您需要发布整个内容。

标签: java recursion helpermethods


【解决方案1】:

我在第二种方法中看到的第一个问题是,您只在声明时返回一些东西

if (this.k.compareTo(k) == 0)

是真的。

编译器应该给你一个错误,因为你的方法被声明为返回List&lt;K&gt;

private List<K> someMethod(K k, List<K> L, int n)

要解决这个问题,您应该在每个 if 语句中或在方法的底部返回一些内容。根据您的逻辑,当找不到满足上述 if 语句的匹配项时,您希望返回一个错误值。因此,例如,您可以通过将此语句放在方法的底部来返回 null

return null;

或者,如果您不想处理 null 值,则返回一个空列表:

return new ArrayList<K>();

如果您进行此更改,您的代码可以在我的机器上正常编译。

这是一个Ideone example,可以很好地按照我建议的更改进行编译。

此外,正如 @ajb 在 cmets 中提到的那样,您并没有真正关注递归的基本情况。

意思是,你没有改变参数:

K k, List<K> L, int n 

当你通过递归传递它们时你的递归方法,因此在没有元素满足条件的情况下将导致“无限”递归导致StackOverFlowError

if(this.k.compareTo(k) == 0) {
    L.add(this.k);
    return list;  // this returns from recursion but nothing else
}

您应该定义某种基本情况,无论您是否找到匹配项都会停止递归。

【讨论】:

    【解决方案2】:

    您的辅助方法缺少最终的返回语句,这可能会弄乱语法检查,并以这个奇怪的错误消息结束。

    private List<K> someMethod(K k, List<K> L, int n) {
        if (this.k.compareTo(k) == 0) {
            L.add(this.k);
            return list;
        }
        if (this.k.compareTo(k) < 0) {
            right.someMethod(k, L, n); //error here
            L.add(this.k);
        }
        if (this.k.compareTo(k) > 0) {
            left.someMethod(k, L, n); //error here
            L.add(this.k);
        }
        return L; // change here, errors should be gone now
    }
    

    【讨论】:

    • 没有。缺少return 语句不是语法错误。它们是错误,但它们不会被关心语法的编译器部分捕获。
    • @ajb,是的。如果返回类型不是void,编译器要求我们总是返回一些东西。
    • 请仔细阅读我所说的内容。它们是错误,但不是语法错误。这种错误不会使编译器混淆,将错误放在不同的行上。
    • 人们可能会争论错误的类型。我认为 ajb 是正确的,因为 Parser 对 AST 执行返回语句检查,因此它可能是语义错误。尽管如此,这是/曾经是问题,现在已解决 =)
    • @ajb,很抱歉没有仔细阅读。我明白你现在的意思了。
    猜你喜欢
    • 2014-05-03
    • 2012-12-09
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2020-06-06
    • 1970-01-01
    • 2021-05-20
    • 2012-04-29
    相关资源
    最近更新 更多