我正在尝试定义递归几何函数,该函数将询问用户序列的第一个值和序列的乘数值。该函数应该给出一个所需长度的序列作为参数,并产生该长度的任意几何序列的列表作为返回值。作为一个澄清示例,如果用户提供5作为起始值而3作为具有所需长度6的乘数,则任意几何序列的前6个元素将是[5,15,45,135,405,1215]
当我运行此代码时,我以奇怪的随机顺序获取序列。到目前为止,这是我的代码:
# This will define a recursive arbitrary Geometric sequence function
def recursive_geo_helper(length):
start = int(input("Enter the first value of the sequence: "))
multiplier = int(input("Enter the value that must be multiplied: "))
return actual_recursive_geo(length, start, multiplier)
def actual_recursive_geo(length, start, multiplier):
sequence = []
# print(start)
if length <= 1:
exit()
# return sequence
else:
sequence.append(start)
start = start * multiplier
length = length - 1
return actual_recursive_geo(length, start, multiplier)
#recursive_geo_helper(5)
print(recursive_geo_helper(6))
答案 0 :(得分:3)
遗憾的是,您的代码没有多大意义。以下是它的一些问题:内置exit
永远不应该在shell之外使用,你的函数不会返回基本情况,即使它没有,它也不会递归地附加到那个基本情况。
解决所有这些问题,这就是你的递归解决方案。
def actual_recursive_geo(length, a, r):
if length <= 0:
return [] # base case
else:
return [a] + actual_recursive_geo(length - 1, a * r, r) # prepend to your base case
虽然这样做效率有点低,因为它会进行大量不必要的列表连接..
让我建议从头开始使用更合适的数据结构来表示无限序列:生成器。
发生器可以懒惰地表示无限序列。此外,Python为您提供了itertools
标准库来操作它们。在这里,我们将返回一个生成器,并使用itertools.islice
对其进行切片。
import itertools
def geometric_input():
"""
Prompt the user for an initial value and a ratio
Return the corresponding geometric series
"""
a = int(input("Enter the first value of the sequence: "))
r = int(input("Enter the ratio: "))
return geometric_sequence(a, r)
def geometric_sequence(a, r):
""" Return a generator for the sequence x_i = a * r ^ i"""
r_exp = 1
while True:
yield a * r_exp
r_exp *= r
seq = geometric_input()
first_elements = list(itertools.islice(seq, 6))
print(*first_elements)
这是输出。
Enter the first value of the sequence: 5
Enter the ratio: 3
5 15 45 135 405 1215
关于生成器的另一个好处是元素在生成时被消耗。这意味着如果再次对生成器进行切片,您将获得序列中的下一个元素
next_elements = list(itertools.islice(seq, 6))
print(*next_elements)
# prints: 3645, 10935, 32805, 98415, 295245, 885735
答案 1 :(得分:0)
我相信你的问题是你在声明函数中的序列并且没有正确地返回它。
此外,如果我们要使用递归,我们可以更进一步,避免通过将修改后的变量传递给递归调用来改变我们的变量。
def geo(sequence, length, multiplier):
if length <= 1:
return sequence
else:
return sequence + geo([sequence[-1] * multiplier], length - 1, multiplier)
以下是REPL的输出:
>>> geo([5], 6, 3)
[5, 15, 45, 135, 405, 1215]
P.S。我更像是一个JavaScript而不是Python人,所以我首先在JS中完成它然后移植它。
这是JavaScript中的等效函数:
function geo(sequence, length, multiplier) {
if (length <= 1) {
return sequence
}
return sequence.concat(geo([sequence.slice(-1) * multiplier], length - 1, multiplier))
}
console.log(geo([5], 6, 3))