我有一个深度递归函数,即使在大输入的情况下理论上也应该可以很好地工作。问题是在撰写本文时我忘记了C#没有很好地进行尾调用优化,如果有的话,所以我得到StackOverflowException
s用于任何复杂足够的输入。该方法的基本结构有两种大方法,每种方法都调用另一种方法。
public object Simplify(object param) {
if (IsSimple(param))
return param;
else
return Expand(param);
}
private object Expand(object param) {
return Simplify(ProcessExpansion(param));
}
IsSimple
和ProcessExpansion
都有相对固定的堆栈深度 - 唯一的问题是Simplify和Expand之间的递归。你会如何在这里减少堆栈深度?
我正在考虑返回会计算结果的代表,但这看起来有点矫枉过正 - 必须有一种更简单的方法。这是我对解决方案的想法(它不是很精致,因为我一直认为我必须在这里做一些可怕的错误):
public object Simplify(object param) {
object result = () => SimplifyInternal(param);
while (result is Func<object>)
result = ((Func<object>)result)();
return result;
}
private object SimplifyInternal(object param) {
if (IsSimple(param))
return param;
else
return Expand(param);
}
private object Expand(object param) {
return () => SimplifyInternal(ProcessExpansion(param));
}
所以我的两个问题是:
答案 0 :(得分:8)
这不是
while(!IsSimple(param))
param = ProcessExpansion(param);
return param;