2009-09-17 74 views
2

是的,我知道措辞很难理解,但是这是让我感到很困扰的东西。在最近的一个项目中,我有一个递归的函数,并且有很多条件会导致它停止递归(目前为三)。哪种情况是可选的? (I.E.最佳性能或最简单的维护)。有条件地执行一个函数的最好方法是什么?

1)条件回报:

void myRecursingFunction (int i, int j){ 
    if (conditionThatWouldStopRecursing) return; 
    if (anotherConditionThatWouldStopRecursing) return; 
    if (thirdConditionThatWouldStopRecursing) return; 

    doSomeCodeHere(); 
    myRecursingFunction(i + 1, j); 
    myRecursingFunction(i, j + 1); 
} 

2)包裹在整个事件中的if语句

void myRecursingFunction (int i, int j){ 
    if (
     !conditionThatWouldStopRecursing && 
     !anotherConditionThatWouldStopRecursing && 
     !thirdConditionThatWouldStopRecursing 
    ){ 
     doSomeCodeHere(); 
     myRecursingFunction(i + 1, j); 
     myRecursingFunction(i, j + 1); 
    } 
} 

3)你就错了小白,任何理智的算法将永远使用递归。

+0

第一个例子等同于在第二个例子中使用||,所以二者不会相同。 – 2009-09-17 20:56:29

+0

@Lasse - 咦?如果这让你感到困惑,我也会否定条件。 – MiffTheFox 2009-09-17 21:01:12

回答

6

这两种方法都应该在幕后产生相同的IL代码,因为它们是等效的布尔表达式。请注意,每个终止条件将按您编写的顺序进行评估(因为编译器无法确定哪一个最可能),因此您需要首先使用最常见的终止条件。

尽管structured programming指出第二种方法更好,但个人而言,我更喜欢将代码返回条件作为递归方法顶部的单独块。我发现更容易阅读和遵循(虽然我不是在方法体的随机区域中返回的粉丝)。

3

我会选择第一个解决方案,因为这使得它完全清楚停止递归的条件是什么。 它更可读,更可维护imho。

1

我喜欢的变体1更好...

这是很容易阅读,然后变种2.在这里,你必须了解3个否定,并与连锁它们组合在一起。我知道它不是“硬”,但它需要更长的时间,然后观察变种1

3

如果是需要快速的东西,我建议尽可能快地打最常见的情况(即将基本情况放在最后,因为您只会打一次)。还可以考虑在递归子句之前放置一个基本的case-1(即,在再次调用该函数之前执行测试,而不是在进入后续调用时检查它),如果这会有所作为。

而且,尽管如此,除非是问题,否则不要优化。我会先澄清一下。

+0

我怀疑这是否有所作为。在递归之前,您仍然必须测试基本情况,而不管回报的顺序如何。 – recursive 2009-09-17 21:54:17

+0

如果它是 - 或者是的。我在考虑具有多于一个流的函数(例如,switch/case语句或嵌套的if语句)。但是对于这个问题,是的,你是对的。 – Joe 2009-09-17 22:27:42

0

我的投票也是选项#1。我看起来更清楚。

相关问题