我是Python的新手。现在我正在学习递归。我不知道此功能如何工作。
此功能必须将两个数字相乘,而不能进行乘法运算。它只能使用自身(递归)。 如果num不为0,此代码如何工作?它像循环直到其0一样工作吗?它有效,但是我不知道如何。
font.axis=2
答案 0 :(得分:0)
它将创建如下堆栈:
mult(4,0) -> return 0;
mult(4,1) -> return 4; (0+4)
mult(4,2) -> return 8; (2*4)
mult(4,4) -> return 16; (2*8)
mult(4,5) -> return 20; (16+4)
顶部堆栈函数调用的结果将返回到堆栈中其下方的函数调用。 要直观地了解此视频,https://www.youtube.com/watch?v=kepBmgvWNDw
答案 1 :(得分:0)
首先,您不必检查变量a
是否等于0。因为它从未改变。对于任何递归步骤,您始终传递相同的a
。
第二,您的函数将达到状态b == 0
,因为在每一步中,您都将b
的值减小为1个单位或b/2
单位。因此,它将达到0。
答案 2 :(得分:0)
您知道乘法是数字本身的N倍的累加。对?所以2 x 4 = 2 + 2 + 2 + 2。
第一个参数采用基数(a),第二个参数采用N次重复(b)。如果数字不为0,会发生什么?
如果b大于0表示我们仍有重复数求和为基数(a)。那么,如何告诉我们要再次求和呢?做相同的功能但是我们将1次重复减去重复次数(b)
mult(a, b-1)
此外,我们需要将下一个多位乘积加到我们的基数(a)中,所以我们将(a)本身加起来:
mult(a, b-1)+a
如果b为0,那么我们完成了,因为我们完成了重复次数。
如果a为0,我们甚至都没有开始,导致0 x N = 0
我不知道第二个条件是什么,我认为这是不必要的。
答案 3 :(得分:0)
考虑一长串加法(所有乘法都是):
3 * 15 == 3 + 3 + 3 + 3 + 3 + 3 + 3 + 3 + 3 + 3 + 3 + 3 + 3 + 3 + 3
执行此操作的幼稚方法是一次添加一个词。
3 * 15 == 3 + (3 + (3 + (3 + (3 + (3 + (3 + (3 + (3 + (3 + (3 + (3 + (3 + (3 + 3)))))))))))))
== 3 + (3 + (3 + (3 + (3 + (3 + (3 + (3 + (3 + (3 + (3 + (3 + (3 + 6))))))))))))
== 3 + (3 + (3 + (3 + (3 + (3 + (3 + (3 + (3 + (3 + (3 + (3 + 9)))))))))))
== 3 + (3 + (3 + (3 + (3 + (3 + (3 + (3 + (3 + (3 + (3 + 12))))))))))
== 3 + (3 + (3 + (3 + (3 + (3 + (3 + (3 + (3 + (3 + 15)))))))))
== 3 + (3 + (3 + (3 + (3 + (3 + (3 + (3 + (3 + 18))))))))
== 3 + (3 + (3 + (3 + (3 + (3 + (3 + (3 + 21)))))))
== 3 + (3 + (3 + (3 + (3 + (3 + (3 + 24))))))
== 3 + (3 + (3 + (3 + (3 + (3 + 27)))))
== 3 + (3 + (3 + (3 + (3 + 30))))
== 3 + (3 + (3 + (3 + 33)))
== 3 + (3 + (3 + 36))
== 3 + (3 + 39)
== 3 + 42
== 45
哇!新增十四(14)个。这将对应一个类似
的定义def mult(a, b):
if b == 0:
return 0
return a + mult(a, b -1)
但是有更好的方法。如果我们对添加项进行不同的分组,则可以重用一些添加项的结果。
如果我们有偶数个值,我们会将它们分为两组,但只将其中的一个相加。无需将其他组相加,我们只需将第一组的结果相加即可。如果值的数量为奇数,我们将其保留为一个,将所得的偶数值相加,然后将奇数加回去。
3 * 15 == 3 + (3 + 3 + 3 + 3 + 3 + 3 + 3) + (3 + 3 + 3 + 3 + 3 + 3 + 3)
== 3 + 2 * (3 + 3 + 3 + 3 + 3 + 3 + 3)
(我写了2 * t
而不是t + t
来强调t
只需要计算一次,我们实际上将2 * t
计算为t + t
避免任何显式乘法。
我们以相同的方式计算子序列。
== 3 + 2 * (3 + (3 + 3 + 3) + (3 + 3 + 3))
== 3 + 2 * (3 + 2 * (3 + 3 + 3))
再来
== 3 + 2 * (3 + 2 * (3 + 2 * (3 + 0 + 0)))
3 + 0 + 0
在那干什么?它使我们可以进一步分解仅一个值的“序列”作为该值加上两个0长度序列之和(因为0是偶数)。长度为0的序列加起来微不足道:其总和为0。
一旦我们完成了分组,就该添加了。请记住,我们正在使用2 * t
计算t + t
。
== 3 + 2 * (3 + 2 * (3 + 2 * (3 + 0)))
== 3 + 2 * (3 + 2 * (3 + 2 * 3))
== 3 + 2 * (3 + 2 * (3 + 6))
== 3 + 2 * (3 + 2 * 9)
== 3 + 2 * (3 + 18)
== 3 + 2 * 21
== 3 + 42
== 45
那只是8个加法!
通常,用于计算a * b
的幼稚方法需要O(b)加法。这种递归方法只需要添加O(lg b)。